 Thank you, everyone, for coming. This talk is on the PHP FIG, or Framework Interoperability Group. My name is Larry Garfield. You may know me online as Krell. If you want to make fun of me on Twitter during the session, that's where you do so, I highly encourage it. I'm the director of Runtime's Integrations, Engines, and Services for Platform SH. Yes, the acronym is deliberate. We are a Platform as a Service development tool slash hosting company. And we have some really cool stickers and patches here, if you want. There's also the web services lead for Drupal 8, which means you can blame me for about a third of the things that changed. I'm the Drupal representative to the PHP FIG, so I have been part of the story that I'm about to tell. And yes, I do implement Huggable, more on that later. So what is PHP FIG? Well, it's a really cool painting by this artist, and integral stuff. Rebecca Simonson, her husband, is the lead on the Sculpin project, and now works for Censio Labs in the US. So really good art on a lot of different open source projects. I actually have this one hanging on my wall. That's why I like to start with that one. So what is FIG, Framework Interoperability Group? What is this thing? When I first proposed this talk, it was going to be a bit different because we were hoping to finish some changes to the answer to this question before I started. That didn't happen because everything's behind in technology. So what is FIG is kind of an open question at this moment. What do I mean by that? Well, let's start with what in hindsight I like to call Framework Interoperability Group 1.0. Back in the bad old days, PHP had no common conventions or standards. Every project did its own thing, and none of them could talk to each other. And the closest thing there was to the ability to share code was Pair, who actually managed to get Pair working. Wow, I expected like three people. How many people enjoyed the process of working with Pair? There we go, no hands up this time. That's more like it. For several years, there were a lot of people working in a lot of different areas and a lot of different projects trying to fix that problem and trying to get PHP projects working together more and collaborating more and sharing more code. And one of the watershed events for that was at the PHP Tech Conference in Chicago in May of 2009. I was not there at the time, but a number of project leads and other key people at a number of PHP projects were there. And PHP 5.3 was coming out in a month or so. And these developers looked at each other and said, you know, PHP 5.3 has this cool thing called namespaces. Maybe we should actually use them the same way in all of our projects. Would that be useful? And they said, well, yes. So they got together at the hotel in a smoke filled room and hammered out a way to collaborate and share a usage pattern for namespaces. Disclaimer, I was not there, so I cannot guarantee there is smoke. My understanding is it was actually just after lunch, not the middle of the night, and it was light outside. But dark smoke filled room makes a much better image. And they came up with something that they called PSR0. PSR standing for PHP standard recommendation, 0 because geeks counted 0. And it was a fairly short common standard for auto loading and namespaces. Heavily inspired by the way Java worked and by the way Pear worked at the time. You ever take the fact that Pear didn't have namespaces? And it was fairly basic. Didn't do all that much, but it didn't need to be. But it provided some common way to handle auto loading of classes between different projects that you could count on. Projects using it all auto loading their code in the same way, which means you could use a single common auto loading pattern. And they came back. And since some of them had admin access on PHP.net, they set up a mailing list, PHP standards, at lists.php.net, and announced to the world that there is now a PHP standards group. And here is our auto loader that we shall all use for all the community to share and then take and use. And the community came back and said, who the hell are you? Because PHP was not used to working together or being told what to do. Everyone was used to doing their own thing, and who cares about anyone else? So yeah, this went over like a lead balloon. They were very quickly thrown off of lists.php.net. They were told very clearly get out. Initially, the plan was to have a closed mailing list, which was totally incompatible with the way PHP.net worked. So they moved to Google Groups and didn't quite make it a closed list. It was a semi-closed list initially. Throughout the course of 2009, they admitted a couple of new projects as members. Of course, whether it was a project or a person was kind of a fuzzy situation. This is when Drupal was added. I was invited in as the Drupal representative. And it basically did nothing for a year. I actually went back and checked the archives. There were four messages to the mailing list in the entirety of 2010. Good. Finally woke up in 2011 sometime and started talking, but not actually being useful because geek's online, I guess, or something. Finally in 2012, this is now three years into this mailing list-slash-groups existence. It started actually being useful. One of the first things it did was rename the group from PHP standards to the Framework Interoperability Group, or FIG. Why? Well, despite the name, it's not just about frameworks. In fact, the majority of projects involved in FIG today and even since 2012 are not frameworks. Many of them are standalone libraries. Many of them are applications like Drupal. Is Drupal a framework and application? I don't know, whatever. And because calling it the PHP Interoperability Group would have given a much less pleasant name, or acronym. One person's laughing anyway. And it kind of actually became useful at this point as an organization. Okay, so what's this group actually going to do? Well, the website at least says this. We are a group of established PHP projects whose goal is to talk about commonalities and find ways that we can work better together. Nice vague wishy-washy statement. What it does is debate and discuss and vote on PHP standard recommendations, which are basically like the RFCs you get from Internet Engineering Task Force, but for PHP, or more like PIPs in Python or JSRs in Java. Same basic idea. And the scope was pretty much anything that could be standardized that improves collaboration and interoperability between member projects. Okay, that's fair. There are a lot of problems with that. And this kind of changed in 2013. And at Fig.2, I would call kind of the United Nations of PHP with all of the positive and negative implications that analogy has. So in 2013, there were two big questions that came up that people were debating in the group. One was, so are we a group of projects or are we a group of people? Because the original setup, it wasn't even a charters, the original common convention was a little of each. It was cool people, but you were defined as cool by the fact that you were a project lead, which was a very poor definition of cool. The other was there was really no structure to how PSRs were worked on other than, well, eventually vote on something. It was, it had astute any form of organization. And so in 2013, we started getting semi-formal working groups. And these were two different votes that were called. First one, the idea that as of today, Fig is an organization of projects, not people. Projects are voted in by the voting representatives of various projects who may or may not be a project lead. I'm not the project lead of Drupal, but I am the Drupal representative to Fig. So I technically represent Dries. And then projects can change their voting rep at any time. They do that sometimes. Some projects, the voting rep kind of works on their own. Some, the voting rep is the project lead. Some, the project rep goes back to some committee on their project and talks about stuff before making a vote. They're currently about 38 projects as of this past weekend. And ultimately, project reps are answerable to their projects as if they're essentially ambassadors to a PHP UN. It is the effective analogy. So is this readable? Not at all, I apologize for that. But we have project representatives who represent a member project. And then any time you have a new PSR proposed, there are three key people involved in that. One is the editor, who can be anyone. And then two sponsors who have to be voting representatives. This is a way to say, okay, there's enough interest in standardizing something that it's worth our time to consider. And that's a vote of, you need to have two sponsors for that. And then a vote of the member projects to say, yes, we will, we're okay with working on this. And then there's also, we've just recently added elected secretaries to deal with the bureaucracy and paperwork involved in running a standards group. Which there is actually a fair bit of. Pretty much the only thing that is limited to those voting reps is voting. So the mailing list is these days open. Anyone in this room can partake of discussion. Anyone in this room can be an editor. Anyone in this room can work on a spec. The only thing that is restricted at all right now is actually voting to approve things. And that's limited to the voting reps. The process today, as of this FIG 2.0 model, you've got an idea. Someone has an idea for a specification. And they bring it up and discuss. They get two sponsors for it. And there's an entrance vote for the spec. If that passes, then this is just an idea. It doesn't have, it's not fully fleshed out. It's, hey, we should standardize X. We should have an interface spec for X or whatever. When it gets voted in as just a concept, the entrance vote, it goes into a draft state. It gets a number at this point. So just because something is PSR and a number doesn't mean it's approved yet. There's unlike IETF where they assigned the number at the last second. In FIG, the number of a standard is specified when we say we're gonna start thinking about it, basically. At this point, you work on it. The editor owns the spec. They're the one with final authority on what goes into it. But take interest from all comers. Get right on it, revise it, throw it out and start over, whatever you're gonna do. Until at some point, the editors and coordinators say, you know what, good enough. Hey, other members, please review. This is essentially a release candidate stage. Very few changes are allowed to the spec. This is all in public before this, but this is when a lot of people first start paying attention, frankly. And only minor changes are allowed. This is for spell checking, editing, and so forth. And the draft process can take any amount of time, anywhere from a few weeks to a few years. Review phase has to be at least two weeks, but can be longer than that. Again, it depends on what is needed for that spec. And then there's a vote. And if it is approved by the other members, then great. We now have a new spec for PHP, which you are under no obligation whatsoever to pay attention to. FIG has no binding authority on anything, including its own member projects. Everything is recommendations only. So that team again is the editor who owns the process sponsors. The coordinator who is originally supposed to be kind of the secretary and process person for that spec. But then we added the secretaries for FIG itself, so those seem kind of irrelevant. And again, anyone can contribute not just these three people. Lots of spec have a number of people working on them. So that's what we are today. This is FIG today, but there are a couple of problems. First, on paper, we say that FIG is a collection of projects, not people. But let's be perfectly honest, people are still people, you're still talking to people. And it's hard to separate the person from the project they represent, both as a project rep and talking to other project reps. There's even one or two people who just kind of ignore the fact that we had this vote and still insist that we're about people, even though they're wrong. A lot of voting reps are busy. They're project leads. They are initiative leads or the equivalent in their project. They've got other things in their mind. They're not actively engaged in every PSR and sometimes they forget to vote. We've actually had a number of votes that didn't get to quorum because people are just busy, not around. Because we've conflated paying attention, supporting FIG's goal and being one of the cool kids. So projects will join and then do nothing after they've joined because, well, they joined to say that they were part of FIG and we would hope that the people involved were doing something and being engaged but they aren't always. It also means that very often we don't really have domain experts working on something. If you have a spec coming up on caching which is an actual spec that we have, then it really helps to have caching experts involved but a lot of the caching experts in the PHP space aren't involved in FIG and don't know about it. You don't know that the spec's happening. So now what do you do? How do you get the right people in the room just because your project lead doesn't actually mean you're the right person to be in the room? And also, who is FIG for? Is it just for member projects and ignore everyone else? There are people who feel that it should be that way. In practice, that's kind of impossible because when a large number of projects adopt something, everyone else gets pressure to do so. Who has seen any of the debates around the PSR2 coding standard? Couple of people, yeah. Drupal doesn't follow the PSR2 coding standard. We'll talk about that in a bit. But there is regular pressure for us to do so because it's the default in PHP Storm because all of the third-party code we pull in our vendor libraries using that style which makes us odd man out. We're not required to adopt it but any project is going to have pressure to follow popular PSRs simply because that's the way networks work. That's the way human networks work. And based on actual surveys we've done, most of the PHP community sees us as a standards body at this point for all of PHP, not just for member projects, for exactly that reason because there's a vacuum there and FIG fills it whether it wants to or not. So, last year, end of last year, several discussions happened around, okay, how do we fix some of these problems? And this turned into a proposal by me primarily called FIG3 which everything I'm about to say is caveated with, this is not finalized, this is actually in voting right now for whether or not to adopt this. So this is a possible future in a week or two. Actually, end of this week. And as I said, I am the primary author of this proposal so what I'm about to say is incredibly biased, bear that in mind. The way to try and address these problems that we've identified is basically embrace the fact that we're a standards body and model ourselves on other standards bodies that have figured out how this works, in particular the IETF. So we still have member projects, but since most of the member project representatives don't actually do anything on a regular basis, we add what we're calling a core committee which is an elected group of people, elected by project representatives and everyone else working on PSRs, everyone involved in FIG who are supposed to, are then basically required in their job description to be paying attention and to look at the big picture of FIG, big picture of several specifications. Meanwhile, we have a more formal working group defined for PSR, at least five people, editor, a core committee member who's a sponsor and at least three other people who again, all but the sponsor can be anyone involved in PHP. You don't have to be blessed in order to do so, anyone can be involved in that. And they're charged with actually developing a working group, or developing a specification. Why? Well, we can get actual domain experts involved in that. There's a minimum of five people involved so you kind of have to dig up and find the people involved in that. If you're working on a spec for something that's going to affect these four projects, you want those four projects actively involved. But these other projects that are not really going to be impacted that much, have a reduced role, because they should. There's been talk of having FIG work on specifications for promises in PHP. So who knows promises from JavaScript? Promises in PHP to do asynchronous PHP. Yes, it's a thing, it's really kind of cool. As the Drupal representative, I have nothing to offer on this front. The people who write async libraries in PHP should be the ones striving that, not me. That's what we get here by having a more focused working group. So the working group again is an editor who acts as a gatekeeper, can be anyone, a sponsor who acts as a bridge to the core committee and provides oversight and guidance, and other people. That core committee, as you said, are elected and they're not project-based. They do not have to be project representative. Anyone is eligible to be a core committee member if they're voted in. They're voted in for a two-year term, we stagger it, so they do need to get re-approved by people periodically, so you don't get the elected for life and then just sit there and do nothing except have a line on your resume problem. And they focus on the big picture of FIG. They focus on are all of these specifications compatible with each other? Are we following trends in the language? Did we actually bother to reach out to this project that would be impacted by the spec, so they had a fair say? That's the kind of thing the core committee is responsible for, that kind of big picture oversight of the work that happens. Because we now have a more formal working group, we can add an extra check for the process as well. So in FIG three, we have germination of an idea, put together a working group. The core committee now is responsible for the entrance vote, which means it's the people who have stepped forward and said, yes, I will always be paying attention and looking at that big picture. And then assuming it passes, a working group works in the PSR, can be more than five people if appropriate. And then rather than just the editor saying, I think it's done, the whole working group has to agree it's done. There's a working group vote of two thirds, so there needs to be broad consensus to adopt a specification. And once they've decided, okay, yes, this is good, we're done with it, then it can go into review. And at this point, under the current model, you can vote on this within two weeks. In FIG three, we're saying, you have to actually use it first. Just like IETF, there needs to be at least two working implementations. If a specification isn't like an interface or something, then that's kind of fuzzy what an implementation is, but you have to show that this thing can actually work in practice before you can have a final vote on it. It has to actually be tested in production. And then the core committee provides the final approval. Again, a two thirds vote so that you have broad consensus and broad support for it. This process is basically a slimmed down version of how the IETF works, which provides, again, forces that broad consensus, gets the people who are impacted in the room, and the people who are directly impacted have more say than those who aren't, which is how it should be. And we have people who are actively, steering the process as a whole. That's the proposal. That's the proposal that FIG is currently considering and voting on. Is it going to pass though? Well, the vote ends Friday, so we'll find out. As of last night when I was putting together these slides, it was currently 12 votes yes, five no with two abstains. Checked earlier today, we've had a couple more votes, so I think it's now 14 to seven. Maybe it's 15 to seven, something like that. So probably. I can't guarantee it, but probably this thing will pass. And this is where I was hoping to have an answer to this question before this talk, but such as life. So that's FIG, that's what it does. Totally forgot to mention here. FIG3 also has a proper mission statement, which we haven't had before, who's had gone through organizations that don't have mission statements. Sucks, doesn't it? Yeah, FIG3 actually has a mission statement which talks about serving the whole PHP community, not just member projects. So what have we done? This is a lot of politics and process and mumbo jumbo. How does this actually benefit us as developers? Well, there are a number of specifications that are published now in widespread use throughout the PHP world. We've roughly split them into hard specs and soft specs. Hard specs are more developer oriented, soft specs are kind of process oriented. The hard specs, PSR0 is the original one, that's been replaced by PSR4, which is an updated auto-loading standard. We have a logging specification, we have one for caching. Who is just in David Strauss' caching session? This is the PSR6 he was talking about. And perhaps the most important PSR7 for HTTP messages. Then we also have two soft specs on coding standards. So I'm gonna go through some of these in a very high level cursory, limited detail. For more information, see the actual specifications or talks directly on these topics which we've had a few people come before. So auto-loading, when was the last time you thought about auto-loading while working on PHP code? It's been a while, right? Yeah, that's because it's a solved problem. You use PSR0 or PSR4 and Composer and you don't think about auto-loading anymore. This is a major improvement over PHP 5.1 or 5.2. Who remembers dealing with auto-loading back then? Who remembers clearing the registry in Drupal 7? I apologize for that. I wrote it, I'm sorry, this is way better. This is why we use this now. PSR0, very, very simple, it's a job inspired. Every backslash, every namespace separator should map to a new directory and the class name maps one to one to a file name. As do underscores and that was for backward compatibility with the old pair convention which was the same thing but with underscores. PSR4 updates that a little bit. It gets rid of that weird handling for underscores which makes things simpler and you can shorten the tree. Who's written modules for Drupal 8? The way files are organized in your SRC directory in a module, that's PSR4. That is the PSR4 auto-loader built into Composer which I'm happy to say was built by a Drupal developer and added to Composer just as PSR4 was approved. Andrea, is he in here somewhere? Okay, see Andrea's heading's around here somewhere. Give him a handshake or a hug, I'm not sure which he prefers, but he actually wrote the PSR4 support. And that prefix for like in this case the Krell HTML model is externally configured. Basically you put it in your Composer JSON file. Like this, you name of your library, auto-load PSR4, things that begin with Krell HTML model are in that directory relative to where this file is. And you no longer have to think about auto-loading ever again. In practice I will say always use PSR4, PSR0 is obsolete, it still works, Composer still supports it, but really just use PSR4. Even if you don't have the prefix to shorten things, it makes you more compatible or more conventional by not having a special underscore handling. And shameless plug for this library of mine based on Drupal, nice small example. Logging, who's done logging in Drupal 8? It should be all of you because you all said you were writing Drupal 8 modules. PSR3 is a logging interface standard. It is what Drupal uses in Drupal 8. It's all based on PSR3. This is the core of PSR3. It's a single interface for a thing that logs stuff. The most important method is log, which is just a log level message and a context array and the rest of these are just utilities that wrap, log by hard coding a level. The target here is not Drupal. It's libraries that might want to plug into Drupal. It's libraries that want to plug into symphony because then Drupal can have its own custom logging system that any random library we pull in can be compatible with by expecting this interface and then you can throw Drupal's logger into it and suddenly we can log that third-party library. You can throw, if you're in symphony, you can throw monologue at it and suddenly symphony can log that third-party library. Wrong slide. The message also can be either a string or an object that implements two-string. It's also log levels defined. These are based on IRFC 5424. Again, we're just taking known internet standards and making PHP interfaces out of them. Very, very simple. The one odd thing is that context array because context is the second worst variable name in the world after data. The idea here is additional extra stuff, including placeholders. Why do we need placeholders as part of logging? Drupal developers should know the answer to this one. Try logging something with a variable in it and that variable is user data and now your database is gone. Okay, maybe you're logging to syslog or to Redis instead of SQL. Oh, great. Then you just log a script name. Did you realize you could hack a system via its logger? Yeah. You don't know the output where that log string is going to be used in advance so you don't know how to escape it. This is a very common problem that Drupal should be very familiar with and so you provide a placeholder separately. You just use curly braces to indicate this is a variable that will get replaced. Here's a list of variables. This is basically Watchdog or the T function. In fact, it was a pair of Drupal developers who made sure that this functionality made it into PSR3 because well, we know we've run into this problem before. That's the value of collaboration. We found bugs that we can fix for everybody. You can also log exceptions. There's a magic value exception, which means the exception that caused the error. What you do with that? What the logger's gonna do with that? Hey, that's your problem. If you're writing a standalone library, which you all should be doing these days rather than card coding Drupal modules, any logging you do do via PSR3 via this interface because then you're suddenly compatible with Drupal logging, with symphony logging, with Zend logging, with Laravel logging. Any system can plug into it. Same basic idea for caching. Similar goal here is logging. Make it easy for a standalone library to be compatible with whatever cache system you're using. Drupal's cache system, symphony's cache system, Laravel's caching system, whatever it's going to be. I was actually the editor for this one, so again, bias. Contains two interfaces primarily, a cache item and a cache pool. Really works on a repository model here, basically inspired by Drupal because we've had caching problems for a long time and we ran into a lot of these issues. Basic idea here, you have a cache pool, which is just a collection of cacheable stuff similar to a cache bin in Drupal. You can get an item out of a pool by some key name. That item is always a cache item object, which could be a hit or not. You can get the value out of it. If it's not a hit, then you can reconcute it, set a value on it, set it to expire at a specific time or after a specific amount of time, using either date time or date interval. Save it, return it. The standard routine you've seen 100 times in Drupal, but done with proper objects, rather than standard class pseudo objects. It also supports bulk operations. This is primarily useful for cache warming, which we don't really do that much of in Drupal, but you can say, I want to pre-compute and cache 100 different values because they're only gonna rarely change, but I want to just pre-compute them and not have to generate them on a user request. All right, so get an empty item for whatever that thing is going to be. Figure out its value and then save it deferred. Save deferred means save this at some point when we call commit or when we call save again on something else, as long as it gets saved eventually. This gives you in the typical SQL case, we can then write a whole bunch of insert statements in one transaction, which will be faster. You can do that kind of optimization. Other caching backends have different multi-insert commands. Whatever, it's an interface, you do whatever your logic is behind that. You can also get multiple, just like you can in Drupal. Load multiple cache items at once, again, if you know what they're going to be. This is a caching style known as look-aside caching, where in the course of your logic, you look aside to the cache before doing something, it's the most basic because then it's really easy to build read-through caching on top of that. Read-through caching is simply wrap your logic in the cache layer rather than integrating it together, which means when you're using interfaces, this is easy. This is why you should always use interfaces, right? Right? A couple of people are nodding, okay. So we have, yeah. Whatever this expensive stuff is that gets done, we have a wrapper for it that does basically the stuff that we just saw. Get an item with some magic name. If it's not already there, do the expensive stuff, cache it, and then return it. Next request through, then we just return that value, which means that this actual code that does the actual work doesn't need to know about caching, which makes it way easier to unit test. This is a good thing. I would recommend structuring your caching this way. Whether you're using PSR6 or not, structure your cache this way whenever possible. It is also fairly extensible or just designed to be in that you can add sub-interfaces for both the pool and the item together, say to add tagging support or namespace support or various other features. And then you can have a PSR6 extended version. We may in the future have standard extensions from FIG, but you can also build your own if you need to because our subclasses, the normal behavior still works fine. PSR7, HTTP messages, perhaps the most important to date. This is an approved spec. Basically, CGI sucks. CGI is terrible. Common gateway interface, a quick question. Who in this room was born after 1993? Usually this, okay, we do have someone. The standard that PHP uses to talk HTTP is older than some people in this room. It's terrible. It's a specification for calling command line executables. Oh, God. Based on the passing environment variables to a script, which means shoehorning HTTP into environment variables like dollar server, which is terrible. Why is dollar server so weird and mixes so many things together in ugly ways? Because CGI. And also because Superglobals. No comment. If I shouldn't need to explain to you why Superglobals are terrible anymore. HTTP messages should just be objects. It's 2016. You should be doing message passing. So PSR7 is. If you worked with the request and response object in Symphony or Drupal 8, because it's the same thing. It's essentially that idea just abstracted a little bit differently. We have a request interface, response interface, server-specific version, and a couple of others as well. Again, I'm just gonna go over this at a very cursory level. All of these objects are designed to be immutable. So instead of editing them in place and passing them around, every change you make spawns a new object. So if you have a response object, you want to set a status code on it. You're going to get it back a new object with that status code, which means you can change it too. So add this header, add another cache control header, and so on and so on. You keep getting back a new object each time. It's actually very performant because PHP has copy-on-write support natively. So spinning up lots of very similar variables doesn't cost all that much. This also makes the code a lot more predictable. You need a lot less error handling. The whole system becomes a lot more stable when you deal with immutable value objects. It also uses streams, or actually a stream wrapper for the actual content for both the request and the response. Why? Because you really don't want to require it to use a string and then have a string output that is a gigabyte-sized CSV you're generating on the fly, or a 500-megabyte file on disk, because that's bad. So instead, you could have a file stream that you set as a body, or random string, or even use a callback function of some kind, which is similar to what Symphony can do. Again, a lot of this inspired by Symphony's HTTP foundation because that was the old de facto standard for how to do this kind of abstraction. Streams are not immutable because they kind of can't be because PHP's underlying stream system is not immutable. Sorry. Your eyes are also abstracted to an interface because they are way more complicated than you think. They are not just a simple string. It's not just the domain and the path. What happens when you specify a port number or that when you specify a port number, that's non-standard. What happens when you specify no domain? What happens when you specify no origin? There's a lot of weird edge cases that are taken care of by this object, which makes it a lot more portable and predictable than just playing around with parse URL. Not gonna go into detail there, I don't have that kind of time. But it's there. We actually support this in Drupal 8. If you have a controller, if you type in instead of on request, but on the PSR7 request interface, you'll get a PSR7 request object instead, translated from the symphony object. If you return a PSR7 response object, it'll get mapped into a symphony response object and go through the rest of the system, which makes it really easy to take something else outside of Drupal that uses PSR7 and plug it in somewhere. That's by design. It's a very late addition to Drupal 8 that we managed to sneak in, but I'm very happy that we did. Coding standards. PSR1 and PSR2. Basically, these are the most needlessly controversial specs in the history of PHP because everybody has an opinion. PSR1 is actually fairly uncontroversial. It started as a single spec, they got split at the last minute. PSR1 is things that affect your runtime code. So for example, don't use short tags. Please. Your files should always be in UTF-8 character encoding, not in Windows 12.52 or whatever it is. Thank you. Camel case your classes, capitalize your constants, stuff like that. Use an auto-loader of some kind, please. And if you have a given file, it should either declare functions and declare classes or it should have coded executes in the global namespace. One or the other, not both. Pretty much odds are you're doing this already. Most code in Drupal was already following this standard because most well-written code already followed this standard to begin with. So really nothing controversial here. The controversial one is PSR2, which is the more stylistic stuff. For example, it specifies four-space indentation, not tabs, not two spaces, four spaces. It also specifies the one true brace alignments, but only for classes and functions, for four statements and if statements, it's inline. This bugs the crap out of me, honestly. I don't actually like PSR2 and all of the stuff it does, but that doesn't really matter because what's important is that the vast majority of PHP projects don't have to think about their coding standards anymore. And they can just say use PSR2 because that's the default in my IDE and argue about other things that actually matter. So whether you approve of PSR2 or not, you should learn it because that's pretty much anything outside of Drupal and WordPress are gonna be using now. So if you're working with any other system, this is the coding style you'll be following because it's just been adopted by almost everybody. Hopefully updated soon in PSR12, which is in development now. Really just updating for PHP 7, which has a bunch of new syntax in it that's way cool and you should all be using because PHP 7 is way faster and some new updates coming for that soon. Again, see the specs if you want to see what the current status there is. So that's what we've got so far. It's actually quite a bit. A lot of these took a while. There's drama behind some of them, but FIG is producing stuff that actually has an impact on the way we develop and makes code more interoperable. And we've got more in the pipeline. We've got a lot in the pipeline. If you're interested in getting involved in FIG, there's, let's say 10-ish, one, two, three, four, five, six, seven, eight, nine specs currently in some stage of development from just starting to nearly done. So if these interest you, if you are educated in this topic, get involved. These are open for comment right now. I'm gonna go through them very, very briefly. PSR9 and PSR10 are around security best practices for projects, no actual code standards here. PSR9 is around reporting mechanism and a good process for handling security reports. This is for projects receiving information about security advisories. Like you should always have a security at whatever address. Or by the way, don't disclose security errors until you actually fix them. All these kind of best practices that Drupal already follows, frankly. And then PSR10 is a security advisory format. The idea here is that we can have a standard machine readable and human readable format in which to publish security advisories. Similar to what Drupal does now, but in a machine readable format, which means you can build tools that can analyze your code base and say, hey, are there security advisories against my program? I've got 15, 20, 30, third party dependencies. Do any of them have security advisories against them that I need to update for? Basically, there is a tool called Sentiolab Security Advisory Checker. This is, the idea is to build the tools that make an open source equivalent of that viable. Maybe tying into Composer, maybe not. But just, we want to get to the point where you can point your code base and say, do I have a security hole? Yes or no? This seems good to me. Ben, in development for a while, was silent for quite some time. We just recently got a new editor for it, Michael Hess of the Drupal security team. So I have very good faith that when these are done, they will be really, really good because Drupal's security team is awesome. The PSR11 is looking to standardize dependency injection containers. This was actually very controversial. It was one of the closest entrance votes we've ever had. It's very, very simple at this point, just the get and has interface. There are a number of projects already using this in development, or the draft version here in their development systems. Why is this useful? I mean, code shouldn't depend on your container, right? That's why it's controversial. The idea is for factories, places that are going to need to depend on a container to load one of these services at runtime based on user configuration or something, which we have a number of in Drupal. We have a lot of places in Drupal we're doing that, so it is relevant. It's also for delegation. The idea here being a lot of libraries ship with a ton of code you have to wire together to make it work correctly. And that wiring is different for every single container, every single application you put it into, which means you need a symphony bridge, a Drupal bridge, a Zend bridge, a Laravel bridge, and that's just a ton of work. So instead, they can ship a tiny little hard-coded hard-wired container for just those services and the main container of your application can delegate to that. Is that a good idea? I don't know. I'm not working on this on myself. I'm honestly still undecided about it. If you want to give me input as the Drupal rep, let me know. PSR 13, this is one that I'm the editor for. It is nearly complete. It's in review right now. We're just working on naming something. The idea here, standardized hypermedia links, because you have a lot of value objects, a lot of data objects for representing JSON API, HAL, HTML has hypermedia link support, Adam has hypermedia link support. Let's standardize how we work with those so that I can translate from a HAL object to HTTP links on a response object really easily. Kind of an edge case, a narrow use case, but a legit one. There are value objects that are read-only or immutable just like in PSR 7. We've got a link object which has the relationship on it, the href that it points to, and attributes on it, and also a templated flag for HAL. And then also objects can be a link collection. This is the one we're still debating the name on, which means I can have an entity that has links on it. I can just say, hey, entity, give me all the link objects that are relevant to you. And it can generate those on the fly off of user configuration and database date and so forth. There are extended interfaces for them that do the same kind of with whatever methods as PSR 7. There's work on an event manager. This is PSR 14. Basically, simply event dispatcher you've seen in Drupal 8. Same thing, just more abstract and standardized. Still very early, it's not much to say on it yet. The current draft is frankly a little over complicated and over engineered, but we'll get to that. We'll fix that. Some more fun ones. Some better tooling around HTTP messages. PSR 15 and PSR 17. 15 is, excuse me, 17 is HTTP factories. The idea here is that PSR 7 interfaces are great, but at some point someone's gotta create an object. And as soon as you have code that's creating the actual object, you're hard coding that library to one specific PSR 7 implementation. You don't want that. So instead, make it really easy to outsource that to a factory. So whoever's providing that implementation, say Zend's the Ectoros library, which is the most common, or Guzzle has one. It can also provide you with a factory to create those objects. Which means you can write middleware, that's PSR 15, that is completely abstracted away, can still generate responses, but is completely abstracted away from the underlying implementation. Who's worked with StackPHP at all? Or Sylex? Okay. You know how you can wrap HTTP kernel instances around each other in StackPHP and in the symphony kernel model? That's middleware. And ironically, symphony was the first to make it possible to do in PHP, but doesn't use it very much. It has become incredibly popular in PHP in the last couple of years. The Zend expressive library is all built on that. Zend 3 framework is built on PSR 7. Slim 3 uses PSR 7 and wants you to use middlewares and so forth. So we standardize that too. Again, this is currently draft, so it's not necessarily what it's going to end up looking like. But the idea being that you have an interface with, it has a process and a next. This is basically the equivalent of handle in the symphony world. And then your middleware simply has that process method, gets a request, and it's going to return a response. So it can get that response by passing it on to the next wrapped middleware, or creating one yourself off the factory. This way, I can still create a new response, and I can plug this code into Drupal, into symphony, into something using Zend dictoros, into any other implementation, and I am still abstracted away from what the underlying implementation is. That's kind of cool. You need both the factory piece and the middleware piece to make that work. That's why it's two specifications. It's also an effort to simplify caching a bit, because the cache system, PSR6 is very robust, it's very flexible, but if you just need a dumb key-value store, it's more work than some people want. So, PSR16 is just a very basic cache interface. Excuse me. With basic key-value, key of string, value is mixed, whatever. There is a wrapper for it to bridge it to PSR6, which is probably what you'll use 90% of the time. So, if you're writing a library that doesn't have complicated needs, they just need very, very basic caching needs, then you can take any PSR6 library, toss the wrapper at it, and then do basic caching on it. If you want something more advanced, you write to the PSR6 interface. That's what's on the table. That's what's coming down the pipeline as people work on it. In some of these cases, there's active work, and some we need people to get involved. Ultimately, though, FIG's goal, any version, any iteration of FIG, its goal is to encourage collaboration, because collaboration builds interoperability, it builds compatibility, and it makes it easier to build a larger community. A community not just of Drupal, and Symphony, and Zen, but of PHP. And frankly, we've met with pretty good success on this front to date. According to packages, PSR3 has almost 2,000 packages that depend on it. PSR6 has 165, PSR7, over 700 packages depending on PSR7. And they've been downloaded millions of times. There's also roughly the order in which they were approved. PSR3 was the first one approved, then 7, then 6. They're roughly following a similar trajectory. This is the data from packages as of about a week ago. Of course, FIG's biggest success, where it's had the most impact, is PSR8. Which is the huggable interface. I'm the editor for this one as well. Surprise, surprise. Defines two interfaces, huggable and group-huggable. The idea here, you can indicate when you are compatible for hugging, when you want to hug someone, or not. You can have a group hug. Drupal knows all about this, right? Drupal has been PSR8-compatible for years. There's actually a number of implementations in the wild, especially this from Bulgaria, PHP about a year ago. Where we did successfully implement the group hug version. Because at the end of the day, the goal is to make it easier to work together. To be able to inter-operate, to build a better ecosystem. To get projects talking. To get people talking. To have people solving common problems and make it easier to divide and conquer. Easier to say, you know what, I want a cache system. I don't care which one it is. I want a logger. I don't care which one it is. I can mix and match easily. I can plug into any framework easily. There's plenty of discussion happening that's not around PSRs necessarily. About just good practices. Because ultimately the goal is to collaborate better and build a better, more robust ecosystem for everyone working in PHP. Thank you. I have a couple minutes for questions. I don't know if there's a microphone around. If you have questions, I'll just repeat them. Shout it out. I'll repeat it. Context around the recent public blog posts around FIG. Disclaimer. Highly biased opinions follow. When FIG 3 was being discussed, it was not explicitly liked. A couple of the people speaking against it proposed instead. Well, let me back up. I talked about who is FIG 4. Member projects or all of PHP. What's our scope? There are those in FIG who feel that FIG was and always should be interested only in member projects and just ignore the entire rest of the world. That's the minority. But it's a loud minority. There are those, myself included, who feel that that's a wonderful fantasy and that'd be nice, but in practice it's impossible for a group like FIG to not impact non-member projects. So we should be paying attention to non-member projects and just accept the fact that we are the PHP standards group, whether that was the original intent or not. A few people have responded by saying, well, if FIG is the original vision of being just for projects and ignore the rest of the world, then we should just shut down FIG. And if you want to have a standard body on this model, then go make a new organization, don't use the FIG name for it. And some of that discussion has gotten rather heated. And one supporter of the shut down FIG position has been very vocal and very public about his distaste for everything and anything involving FIG 3. And I will stop that description there for the sake of diplomacy. So yeah, that's existential crisis in FIG as we decide are we a standards body or not. And some people standing on soapboxes about that, and of course a lot of FUD. I actually did an article for SitePoint last week. A week and a half ago now. Specifically because someone else not involved in FIG had done an article for them that got most of it wrong. Factually wrong. So I put up a blog post to correct that fact. Because people are paying attention to FIG. And I think I've got time for one more question before I get thrown off the stage here. Outlook for Drupal using PSR2. I think it's going to happen eventually. Not soon. Because technically switching Drupal to PSR2 would be stupid easy. You run a code format across the code base and commit the result. And break every single patch against every single module in the entire system. And that's not even counting the number of people who don't like PSR2 for very legitimate reasons. There are places where PSR2 is just stupid. And the fact that we do have a lot of tooling built up around our current coding standards. And in many ways our coding standards are a lot more detailed than PSR2 is. So it's not it is socially a very difficult transition to make. I think it's probably going to happen eventually anyway. Simply because there will be enough pressure over time. But I'm not pushing that myself. I probably won't push myself more. I am resigned to the fact that it will eventually happen. But I have no clue on a timeline for that. Probably Drupal 9 at the absolute earliest. What changes to suspect in PSR12? No changes for current code. So it's not going to change the brace position or anything like that. It's mostly PHP 7 adds support for return types. Okay. Where do we put the colon? Where do we put the spaces around the colon for return types? Those didn't exist when PSR2 was written. We now have people using declare statements for strict typing. What are the carriage returns around that? That kind of stuff. So it's all stuff that didn't exist when PSR2 came out. And now they do. So okay, we should probably standardize those. Which is also an open question with a small number of people saying don't standardize anything until people are already doing it. FIG should only ever standardize what's already being done. Other people pointing out that's a great way to end up with incompatibility and a lot of people having to break compatibility when we define a new standard. So it should be all backward compatible stuff in PSR12. Thank you all for coming. Please do get involved if there's an area that you have specific interest in and specific domain knowledge. And come up and get one of these cool stickers. I'm happy to answer questions after the session as well. Thank you.