Self-hosted service
24pullrequests/24pullrequests avatar
24pullrequests/24pullrequests

24 Pull Requests: the Rails site that reroutes holiday code gifts

:christmas_tree: Giving back to open source for the holidays

1,707 stars534 forksRubyMIT

At a glance

What is it?
24pullrequests is a Ruby on Rails application that collects open source projects looking for help during December 1st to December 24th, plus a directory of people who want to send pull requests. It is a seasonal catalogue and promotion site, not a matching engine, and its own setup instructions carry a Ruby version contradiction worth reading before you start.
Who is it for?
Adopt 24pullrequests if you run a small open source project that could use a burst of December attention, or if you want to contribute and need a short list of places to start. Skip it if you expected an automated matching or notification service, since the repository shows no such machinery, and if your team needs a production data model you will have to audit, because the Docker Compose file still pins postgres:9.6.
Can I use it commercially?
Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 2 days ago.
What is it written in?
Mainly Ruby, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on October 23, 2026, and from our analysis. They are not legal advice.

Editorial analysis

A December window, not a matching engine

24 Pull Requests is described as a yearly initiative encouraging contributors to send 24 pull requests between December 1st and December 24th. The site exists to promote that idea and to hold two directories: projects that want help, and contributors who want to give some. A visitor starts at the projects listing, or submits their own repository through a project submission form. That is the entire user-facing loop. There is no account-to-project pairing, no difficulty rating, no automated suggestion, and no notification path described anywhere in the repository. If you are looking for a tool that matches a Ruby newcomer to a suitable repository, this is not it.

The repository makes the distinction explicit. The development instructions open with a note that they are for working on the 24pullrequests.com website, and state plainly that if you only want to be a developer who contributes pull requests during the holidays you do not need to follow them, and should go to the site instead. So the codebase serves two audiences: maintainers of the campaign site, and the people the site exists to redirect elsewhere.

Beyond the two directories, the project's shape is conventional Rails. Top-level entries include a Gemfile and Gemfile.lock, a Rakefile, config.ru for Rack mounting, a Procfile, an app directory, config, db, lib, spec, test, vendor, plus design and docs directories. Tests are RSpec with Capybara, run through rake rather than a separate binary. Licence is MIT, so the code can be reused and modified under the terms of that file, though the licence text itself is not reproduced in the README and should be read before redistribution.

Translations carry twenty languages and a Transifex dependency

A detail that matters more than usual for a campaign aimed at contributors worldwide is how the site handles language. The README states that 24 Pull Requests is available in twenty languages, with translations managed on Transifex. Using Transifex requires authentication, which means the editing workflow is not entirely local and a contributor without an account there cannot go straight to the hosted translation tool.

The fallback path is the standard Rails i18n framework. The documented route is to fork the project, create a copy of config/locales/en.yml inside the locales folder, and amend the first line with the correct character set from the file the README links to. From there the file follows the usual i18n convention of nesting keys under locale roots. This is the conventional layout rather than anything unusual, but it means a new language is a pull request against a YAML file, not a registration in some admin UI.

The consequence for an adopter is worth stating plainly. A campaign site whose value depends on reaching contributors outside English-speaking communities has a translation surface that sits partly outside the repository. If you fork this and change the campaign dates or the messaging, you inherit the job of keeping locale files consistent across twenty files, and there is no test in the spec directory that the README describes as guarding for missing keys.

The README contradicts itself on the Ruby version

The local server instructions begin by telling you to install Ruby 4.0.7, then immediately show rbenv commands that install and set a different version. That is not a paraphrase; both lines are present in the same section, one sentence apart.

bash
rbenv install 4.0.0
rbenv global 4.0.0

The Dockerfile resolves the ambiguity in the direction of the prose, since its first line is FROM ruby:4.0.7, and the repository carries a .ruby-version file at its top level that would tell you what the pinned version actually is. So the rbenv block in the README is the piece that is out of step. It is a small thing, but it is exactly the kind of detail that costs an hour when a bundle install fails against a mismatched interpreter, and it is a fair signal about how much of the surrounding documentation is generated from older state.

The rest of the Ruby setup is unremarkable and worth copying verbatim. Install bundler, rehash so rbenv sees the shim, then install from the lockfile.

Postgres first, then three Rake tasks

The application needs PostgreSQL before any Rake task can do anything useful, and the README gives a package manager for each major platform. On macOS the documented route is Homebrew, on Debian-based distributions it is apt-get including libpq-dev for the client headers, and on Windows it is the Chocolatey package. A browser automation tool is installed alongside Postgres on macOS, which hints at Capybara-driven system tests rather than simulated ones.

bash
brew install postgres
brew install chrome-cli

The Debian equivalent installs the server, the contrib module and the development library in one call:

bash
sudo apt-get install postgresql postgresql-contrib libpq-dev

Once Postgres is present, the sequence is short: clone, install gems, create and migrate the databases, optionally seed sample data, start the server. Each step is a separate command, and the seed task is worth knowing about because it fills an empty database with example projects and users, which is the fastest way to see what the schema expects.

bash
git clone [email protected]:24pullrequests/24pullrequests.git
cd 24pullrequests
gem install bundler && rbenv rehash
bundle install

Creating the database and applying the migrations are separate rake invocations, not one combined command, which is why a partially failed first run usually means rerunning the second one:

bash
bundle exec rake db:create:all
bundle exec rake db:migrate
bundle exec rake db:seed

The last line is optional and the README marks it as sample data. For email work it points at MailCatcher, with a note to read MailCatcher bundler documentation first, because this project uses Bundler and the two setups can collide over which gem environment wins. Then the server comes up on port 3000:

bash
bundle exec rails s

and you point the browser at http://localhost:3000.

Docker Compose still points at postgres:9.6

The Compose path is the shortest route to a running site, two commands after the clone. The Compose file builds an app image and starts a database service, with the database reachable by an internal hostname rather than a published port. The command inside the container is bin/docker-start, described as pulling PostgreSQL, creating and migrating the database, and starting the server, so the migration step is handled for you rather than run by hand.

yaml
services:
  database:
    image: postgres:9.6
    environment:
      - POSTGRES_PASSWORD=development

Two things in that file deserve a second look from anyone planning to reuse this beyond a laptop. The database image is postgres:9.6, so verify compatibility before reusing this setup beyond a laptop. And the environment block passes GitHub OAuth credentials straight through from the host shell:

yaml
    environment:
      - RAILS_ENV=development
      - GITHUB_KEY=${GITHUB_KEY}
      - GITHUB_SECRET=${GITHUB_SECRET}

The app image is built from the repository Dockerfile, which pins bundler to frozen mode so that a Gemfile edited without a matching lockfile fails the build rather than silently resolving new gems. It also installs nodejs and netcat-traditional on top of the Ruby base, which the README does not explain and which most contributors will never touch.

bash
docker compose build
docker compose up

After `docker compose up` the site answers on http://localhost:3000, matching the port published by the app service.

Omniauth variables leak between projects and break the suite

One failure mode is documented in enough detail to be worth quoting. Tests run with bundle exec rake, using the RSpec and Capybara setup, and the database for them is prepared with bundle exec rake db:test:prepare, which creates the test database and populates its schema. The README is explicit that you do not need this before every run, but that a large number of failing tests after a migration is the signal to run it.

The sharper trap is the GitHub OAuth environment. The test suite uses the omniauth integration, driven by GITHUB_KEY and GITHUB_SECRET, to learn about contributors and pull requests. If those variables already point at a different project's GitHub application, which is exactly what happens on a machine that develops several OAuth clients, the suite will query the wrong application. The fix offered is to unset the variables before running tests, or to reset them after creating a GitHub application for this project.

The same suite is reachable inside Compose, and the granularity is finer than the bare rake invocation:

bash
docker compose run app bundle exec rake SPEC=./spec/path/to/test_spec.rb
docker compose run app bundle exec rake SPEC=./spec/path/to/test_spec.rb:123

The first form runs a whole spec file, the second a single line number, which is the fastest way to reproduce a failure without running everything.

What this project does not try to be

The clearest way to place 24pullrequests is against the alternative shape of the same idea. A purely static campaign site can list projects as YAML or JSON files, build with Jekyll or Hugo, and host on GitHub Pages, which means no database, no OAuth secrets and no Ruby version to pin.

The Rails application gives up the operational simplicity in exchange for those. Submitting a project, attributing a pull request to a contributor, and rendering counts that come from GitHub rather than from hand-edited files all require a running server and a relational store. The evidence sits in the repository layout: a db directory with migrations, a seed task that populates sample records, an omniauth path that queries GitHub, and a Compose file whose whole purpose is to bring up a database alongside the app.

The trade-off is real in both directions. If your goal is one December of visibility and you already have hosting, the static route is cheaper and has nothing to break. If your goal is a directory that keeps contributor records and accepts submissions without you editing files, this application already has that machinery written and the MIT licence lets you take it. What it does not have is documentation for running it in production, and the README does not address deployment, scaling or backups at all.

Editorial conclusion

Adopt 24pullrequests if you run a small open source project that could use a burst of December attention, or if you want to contribute and need a short list of places to start. Skip it if you expected an automated matching or notification service, since the repository shows no such machinery, and if your team needs a production data model you will have to audit, because the Docker Compose file still pins postgres:9.6. Before anything else, resolve the Ruby version conflict in the README, which says 4.0.7 in one line and 4.0.0 in the very next block, and confirm your Gemfile.lock matches the gems you actually need.

Frequently asked questions

What is 24 Pull Requests and when does it run?

It is a yearly initiative asking contributors to send 24 pull requests between December 1st and December 24th, backed by a Ruby on Rails site that lists projects wanting help and collects people willing to contribute.

What do I need to run 24pullrequests locally?

A Ruby runtime, PostgreSQL, and Bundler. The README's rbenv block installs 4.0.0 while its prose and the Dockerfile say 4.0.7, so check .ruby-version before bundling. You then create and migrate the database with bundle exec rake db:create:all and bundle exec rake db:migrate, and start the server with bundle exec rails s.

How do I run the tests for 24pullrequests?

Run bundle exec rake, which drives the RSpec and Capybara suite. Use bundle exec rake db:test:prepare after migrations if many tests fail, and unset GITHUB_KEY and GITHUB_SECRET first if they point at another project's GitHub application, since the omniauth setup uses them to look up contributors and pull requests.

Official sources

  1. 24pullrequests/24pullrequests on GitHub
  2. Issues
  3. License: MIT
  4. Project website
  5. README
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/24pullrequests-24pullrequests.svg)](https://hysenlabs.com/projects/24pullrequests-24pullrequests)

Was this useful?