I'm super happy to announce the launch of a new website for IndieWeb events at events.indieweb.org!
This website is a place to find and post events for the IndieWeb community. Historically, we've used the IndieWeb wiki to collect events for the community. There are definitely some benefits to this approach, but there are also quite a lot of downsides.
My goal with this new website was to capture the best parts of a community wiki for events, while streamlining the process for creating events and making it easier to find what you're looking for as an attendee.
The rest of this post describes the motivations and design decisions for the website. If that is not interesting to you, you can stop reading now, and just know that it should be a lot easier to find and create IndieWeb community events going forward at events.indieweb.org!
Over the last year or so, I've spent a lot of time talking with organizers of the local IndieWeb events like IndieWebCamps or Homebrew Website Clubs. We've also grown a considerable amount this year, adding new organizers and expanding into new cities.
As we've been onboarding new organizers who are hosting events in their city, I continually see people struggling with the current process of listing an event on the wiki. It's not at all their fault either! Here's an example of what it takes to post a new Homebrew Website Club event, as described on the wiki.
If your event is not on a "regular" Homebrew Website Club day, then you'll need to add a new date to the wiki template of HWC dates, which means editing this template:
Create a page on the wiki for the event, the easiest way is to find a past event and copy the page and modify it for your city. That involves editing a page that looks something like this:
One part of this process that usually gets messed up is that the wiki markup needs to include the h-event Microformats HTML inside the wiki page. This enables some automation that we have, such as generating the IndieWeb newsletter with photos from the event.
It's far too easy to forget to add a closing
</div> or forget the particular syntax for expressing dates and times in HTML and Microformats. I also personally think that it's not very friendly or accessible to make event organizers deal with this kind of low-level markup, and creates a barrier to people who would otherwise enjoy organizing meetups.
If you have a website that supports posting events on it yourself, then you're also encouraged to create an event post on your own website and link to it from the wiki.
Then, you need to make sure the event page is added to indieweb.org/Events so that people will actually find it. That also enables some of the automation like having the bot add it to the home page summary and adding it to the newsletter. Thanks to some wiki template wrangling by gRegor, it is at least a little easier to get the wiki markup right since you can use templates for it:
In practice, relatively few people have actually done this, and usually this ends up being done by either gRegor or Tantek.
At the end of all of this, attendees are left with an experience for discovering and RSVP'ing for events something like this.
Visit indieweb.org/Events to see what's coming next, and you're presented with a list like this:
I'm no designer or information architect, but even I can tell that this page is lacking in some very basic structure that would make it friendly to viewers.
If you manage to find a meetup in your city and click on it, then you visit the event page for the full details.
This now presents its own list of challenges.
So needless to say, this is not a very good experience for event organizers or attendees.
We've talked about trying to improve this situation at various organizers meetups in the past, but never came up with a conclusive plan. I decided that it would be my personal goal to launch a new website to solve these issues so that we can go into 2020 with a much nicer experience for events.
I am happy to say I believe I have addressed nearly all the issues with our current system, while still making it as flexible to use as the wiki.
Here's a quick overview of roughly the feature set of the new events website.
List of upcoming events - the home page is a list of all upcoming events
Tag pages - events can be tagged, and tag pages show all events with that tag! This can be used to create city pages showing events only in that city, for example: #austin.
iCal feeds - every page has an iCal feed you can add to your calendar! You can add the home page iCal feed to get a list of all events, or you can add a tag page feed to get just events in your city.
Microformats - of course every page is marked up with h-event Microformats, so you can subscribe to this in software that supports that vocabulary, or use it as an API for getting events from this website for things like the IndieWeb Newsletter.
Authentication - if you're logged in to the IndieWeb wiki, then you're already logged in here!
Wiki-like editing - anyone who is logged in can add and edit all the details of events, just like if it were a wiki page.
Events have their own permalinks which have the following features:
Cover image - events can have a cover image that shows up at the top. These are always cropped to a fixed size for consistency.
Photo gallery - photos can be added to the event page, and they show up as a nice photo gallery. The first photo is shown full width, and then below that is a grid with the rest of the photos.
The photos can be clicked to view larger, and you can also add alt text for the photos as well. The photos can be re-ordered by dragging them around if you're logged in.
You can either upload photos to the event directly, or you can add photos by posting them on your own website and sending a webmention to the event page!
Related blog posts and comments - event pages can show related blog posts about an event, which is a fun way to capture what people have written after an event. See IndieWebCamp Amsterdam 2019 as an example. If you want to add your own post to an event, just link to the event page and send a webmention!
RSVPs - RSVPs are handled in two different ways. If you're logged in, you'll see an "I'm Going" button on upcoming events. You can click it to add yourself to the RSVP list immediately. The event pages also accept RSVP Webmentions so you can RSVP from your own website.
HTML and Markdown description - the main page for the event supports Markdown and a limited subset of HTML tags for formatting. You can use this to provide full details of an event, or even add things that aren't otherwise supported by the website.
Add to calendar - every upcoming event has an "add to calendar" button which provides both an iCal event as well as a like to add to a Google calendar.
Timezone converter - for events that have a specific start time, the time links out to a page that shows that time in multiple timezones. This is mainly useful for virtual events like Virtual Homebrew Website Clubs, or if you're trying to remotely join another event.
The time of the event is shown along with the time of the event in the timezone your browser reports. Below that is a list of the equivalent times in all timezones used by other events in the website.
One of my main goals with the event URLs was that I wanted them to be meaningful to humans. This means communicating some context about the event from the URL alone.
That means avoiding the URL patterns from Twitter and Instagram which are just a random string.
I opted to go with the pattern:
YYYY/mm/slug-id. This conveys a rough approximation of the date of the event (year and month only). The slug is a generated slug from the name of the event, converting everything to lowercase and removing non-alphanumeric characters, separating words with hyphens. The
id portion is a unique identifier for the event which doesn't change after it's created.
If a post is updated to have a new name, a new slug is generated. Because the permalinks only rely on the unique ID, it doesn't actually matter what your enter for the year or month or slug portion of the URL, you're always redirected to the canonical based on the ID in the URL.
The only thing about this that I'm not entirely happy with is the random ID at the end. I feel like it's taking the easy way out with URL routing at the expense of being friendlier to look at. The upside is that a lot of technical challenges become a lot easier doing it this way, I don't have to store a list of past slugs to support redirects for example, so I thought it was worth the tradeoff in this case. I put it at the end because when a portion of the URL is shown in Twitter or Slack for example, you'd be able to see the most meaningful parts of the URL even if the end is cut off.
I wanted creating an event to be as straightforward as possible. To start with, there's a giant "Add an Event" link in the top navigation bar, which is already an improvement.
One challenge I quickly ran into was that adding fields for all the information needed about the event quickly turns into quite a large form. I didn't want to split it into multiple pages, so instead I broke the page into sections.
To start, you enter the name of the event, and optionally add a cover image. The image will be cropped and a preview will appear immediately.
Next, you'll add information about the location of the event. Ultimately these are just regular text fields, but the "search for a location" box on top can help you automatically fill them out by looking up a location.
If you start typing in that box, it will use the Google Maps autocomplete API to find venues matching your search.
Clicking on one of the options in the list will then fill out the details in the rest of the fields, and you'll see a little map appear as visual confirmation.
Of course you're free to not use the venue search at all and just type in the details manually. Or for virtual events with no physical location you can just enter "Online" as the venue name.
Next up is adding the date and/or time of the event.
If you do use the autocomplete and select a venue, then an additional bonus is that it finds the matching timezone for that location as well.
This is where it gets a bit tricky. I've made a couple of design decisions around date handling to simplify both the data entry as well as presentation of dates and times for events. I'll describe those in detail a bit later.
Lastly, you can add a link to the event's website if it has one, add a description, and add one or more tags.
You'd want to include a link to the event's website if for example it requires that you register for tickets to attend the event. Since IndieWebCamps require ticket registration, we'll be linking out to the individual IndieWebCamp's page to buy tickets. We've been using a pattern of
YYYY.indieweb.org/city for a few years now, and it's worked out pretty well. But if you're adding something like a Homebrew Website Club that doesn't have its own website, you just leave this blank and this page effectively becomes the canonical link for that event.
The description field supports markdown and a limited set of HTML tags for formatting. For events with their own website, I'd recommend leaving this description relatively short. But if you want this page to be the canonical event page, feel free to use multiple headers, embed images, and make it look as nice as you want.
Tags are a great way to collect related events so they can be found easier. I'd definitely recommend adding a tag for the city of the event, such as "austin", so that people can then visit the tag page to find events in their city. You can also add tags like "indiewebcamp" or "hwc" which then provide a quick way for people to find all upcoming Homebrew Website Clubs regardless of location.
Clone event - in order to support quickly adding recurring events like Homebrew Website Clubs, you can click the "Clone Event" button on a previous event, and quickly make a new event by changing only the details you want.
Deciding how to handle dates, times, and timezones was one of the most challenging parts of this project. If you've ever dealt with building systems that handle times and timezones you'll know what I mean.
I decided to have essentially four distinct ways an event can present its date/time on this website.
One-day events - an event that takes place during some portion of one day. This is intended for things like evening events, one-day IndieWebCamps, or other full-day conferences. To create this event, enter only the start date, and enter a start and optionally enter the end time.
Depending on whether you enter a start and end time, the event date will be displayed as one of the below:
If you don't enter a timezone, then these times are considered "floating times" or "local times" and the system doesn't know when it actually occurs. The iCal feed that it produces will also output it as a floating time, leaving out all timezone information. Calendar apps should add this as either a floating time in your calendar, or snap it to your local timezone when you add it. That can cause some edge cases such as when you add an event in the future that will be in a timezone different from where you are when you add it.
If you add a timezone when you create the event, then it will display the timezone there as well as include it in the iCal feed, and you'll avoid the floating time issues.
Multi-day events - an event that spans more than one day, such as multi-day conferences.
I took the liberty of deciding that in this case, the times of the event are never shown. In practice, I find it to be more confusing than helpful when an event is shown as being "January 20, 8:00am through January 21, 5:00pm". Does that mean I am expected to be there overnight? What time do things wrap up the first day? etc. etc. Instead, it's far more helpful for the overall date range of the event to be displayed at the top, and then elsewhere provide the detailed day-by-day schedule. This is how we've handled it with our pages like IndieWeb Summit which show the date summary at the top and a detailed schedule grid below.
So to create multi-day events, you only need to enter the start and end dates. Even if you enter times, they will be ignored by the system. The timezone is also unnecessary in this case because it's not needed in order for something reading the feed to show the same date range.
That will be displayed without any time or timezone information.
If the date range spans a month boundary, then both month names appear of course.
In this case, the iCal feed also omits the times and timezone. That means adding it to a calendar app adds it as a floating date. I've had Apple Calendar and Outlook both mess up multi-day events when there's a timezone specified, so that it looks like the event starts at 5pm local time the previous day, which is really confusing. This should prevent that from happening.
My goal is to eventually open source this project so that others can use it for their own community. I'm actually planning on running a copy of it on oauth.net to collect OAuth community events as well.
That said, I feel like it's not quite ready to open source, so I'm holding off on that for the time being. Here are some of the things I need to solve before I'm ready to publish this.
Remote-Userheader, which is a great way to tie this in to existing authentication systems. I'll need to provide alternatives for people who don't have an existing authentication system already.
My goal is to not have any 2020 events on the IndieWeb wiki! I think this project is far enough along that it can effectively do everything the wiki can do around events and more.
I've already added all the upcoming 2020 events that were on the wiki into the new website. Going forward, it should be significantly easier adding events on this website rather than the wiki. There will only be a little bit of cleanup to do around some of the automations such as the list of upcoming events on the home page and the newsletter.
I'm sure there are some things I forgot to address while building this, so if you're an organizer of any IndieWeb events, please do let me know what I may have missed.
So let me know what you think! I'm really excited to have finally launched this after spending so long designing and building it. Thanks to everyone who helped me talk through the early prototypes of this idea. I'm hoping it makes for a much better experience for everyone who hosts and attends IndieWeb events!
Trying to understand OAuth often feels like being trapped inside a maze of specs, trying to find your way out, before you can finally do what you actually set out to do: build your application.
While this can be incredibly frustrating, it’s no accident that OAuth is actually made up of many different RFCs, building upon each other and adding features in different ways.
In fact, the “core” OAuth spec, RFC 6749, isn’t even called a specification, it’s technically a “framework” you can use to build specifications from. Part of the reason for this is because it leaves a lot of things optional, and requires that an implementer makes decisions about things like which grant types to support, whether or not refresh tokens are one-time use, and even whether access tokens should be Bearer tokens or use some sort of signed token mechanism.
This has often been quoted as the biggest failure of OAuth, but is also a large part of the reason OAuth has been successfully deployed at the largest companies at scale over the last 10 years.
OAuth has been patched and extended a lot in the last decade of experience deploying systems using it. It’s been extended in ways the original authors could never even see coming. Keep in mind that when OAuth 2.0 was published in 2012, the iPhone 5 was brand new, the latest browser from Microsoft was Internet Explorer 9, single-page apps were called “AJAX apps”, and CORS was not yet an established W3C standard.
Since 2012, the web and mobile landscape has changed dramatically. More people access the internet from mobile devices than desktop devices, single-page apps are an extremely common way of creating web apps, and countless password database breaches have time and again demonstrated that storing passwords is dangerous.
It became apparent that a better solution was needed for mobile apps, so PKCE (RFC 7636) was created to provide a way to use the Authorization Code flow without a client secret.
Later, “OAuth 2.0 for Native Apps” (RFC 8252) was published, which recommends that native apps use the Authorization Code flow with the PKCE extension.
A new class of device arose along with a need to use OAuth with them: devices that have no browser or lack a keyboard, such as an Apple TV or YouTube streaming video encoder. An entirely new OAuth grant was created to address this, called the Device Grant, published as RFC 8626.
So what started out as a list of four grant types has had things added and removed, and now looks more like this.
Which, if you look closely, actually ends up distilling down to this:
So what we’ve effectively done is taken the core OAuth RFC, added and removed things, and turned it into an entirely different set of recommendations. The problem is that it requires reading far too many RFCs to understand this landscape.
If you want to implement a secure OAuth solution today, it requires reading: RFC 6749 (OAuth 2.0 Core), RFC 6750 (Bearer Tokens), RFC 6819 (Threat Model and Security Considerations), RFC 8252 (OAuth for Native Apps), RFC 8628 (Device Grant), OAuth for Browser-Based Apps, OAuth 2.0 Security Best Current Practice, RFC 7009 (Token Revocation), RFC 8414 (Authorization Server Metadata), and if you’re also implementing an OAuth server, then you need to read RFC 7519 (JWT), JWT Best Current Practice, JWT Profile for Access Tokens, and probably some others that I forgot. That’s a lot of material.
So why am I suggesting an OAuth 2.1? Surely we should instead scrap this existing work and create something simpler and more streamlined?
As it so happens, that effort is already under way as well, being led by Justin Richer under the name Transactional Authorization, or TXAuth, and likely to end up as OAuth 3. That effort takes a completely greenfield approach, rethinking how OAuth and all its related specs and extensions such as UMA might look if everything were not tied to being an extension of the original OAuth 2.0 RFC 6759. I’m definitely in support of this effort, there are a lot of nice patterns that emerge when you look at it this way, but as we all know, creating a new spec from scratch is not a quick process, much less getting broad adoption within the industry. So while effort on OAuth 3 is under way, which will take literal years to finish, there is room to tidy things up with OAuth 2 in the mean time.
At the OAuth working group meeting in Singapore last month (IETF 106), I led a discussion about OAuth 2.1 and what it should encompass.
My main goal with OAuth 2.1 is to capture the current best practices in OAuth 2.0 as well as its well-established extensions under a single name. That also means specifically that this effort will not define any new behavior itself, it is just to capture behavior defined in other specs. It also won’t include anything considered experimental or still in progress.
There was a general agreement from folks in the room that something like this is needed, and following the official meeting, I led a two-hour breakout session where a dozen or so of us dove into more details and started making a plan.
Torsten, the author of the Security BCP made a comment which I thought framed the discussion well. His goal for OAuth 2.1 is that it should make the Security BCP irrelevant because it already includes everything the Security BCP says. In other words, there should be no need to document the most secure way to implement OAuth, since that should be the only option available when you read the spec.
We still need to discuss the specifics about what form this document will take, whether that is going to be an entirely new RFC that replaces RFC 6749, or a BCP that references the other specs, or something else entirely. However, the overarching goals are:
The specifics of what will be included in OAuth 2.1 are still up for discussion within the group, and will be in the agenda of the upcoming IETF meetings. The starting point for these discussions is roughly the below.
If an authorization server intends to interoperate with arbitrary resource servers, such as OAuth services and open source projects, then there is an additional set of requirements that includes:
Of course all of these points are currently up for debate, so if you have feelings about them, you should definitely join the mailing list and discuss them!
Currently the biggest question for the group is whether or not OAuth 2.1 should make technically breaking changes. It definitely won’t define anything new itself, but if you look at what the Security BCP says, it requires PKCE for all authorization code grants, even for confidential clients. Since most current deployments of OAuth 2.0 only support PKCE for public clients, that means most current deployments will not be compliant with OAuth 2.1 out of the gate. There are arguments on both sides of this, which was a large part of the discussion during the breakout session last month, with no clear consensus.
These are the kinds of questions that will be discussed in the coming months within the group. If you have thoughts, I would be more than happy to hear them! Feel free to send an email to the list directly, or even write a blog post in response!
I’m excited for this work to kick off, and looking forward to many more discussions going forward!