Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
Legacy Redirector for Sculpin 3

Legacy Redirector for Sculpin 3

This class listens to the AFTER_RUN event in Sculpin 3 and locates pagination files (Page 2 and above) in order to generate a placeholder file that matches the legacy version from Sculpin 2. There was a bug in Sculpin 2 that resulted in these files being named like 2.html when the intent was actually to name them 2/index.html for friendly URLs.

The output of the redirector is a very spartan HTML-based redirect. Should be sufficient for convincing search engines and the like to update their mappings.

This has been tested with Sculpin 3.0.0-ALPHA1.

Installation

Append the contents of sculpin_kernel.yml to your existing sculpin_kernel.yml.

Place LegacyRedirector.php somewhere that the composer autoloader can find it. In my case, I used a PSR-4 autoloader definition in my composer.json & ran composer update:

  "autoload": {
    "classmap": ["component-manager.php"],
    "psr-4": {
      "Beryllium\\Whateverthing\\": "app/src/"
    }
  }

Then I placed the file in the app/src/ folder.

Now, when generating your site, you should get both 2.html (containing the HTML redirect) and 2/index.html, containing the actual Page 2 content.

<?php
namespace Beryllium\Whateverthing;
use Sculpin\Core\Event\SourceSetEvent;
use Sculpin\Core\Output\FilesystemWriter;
use Sculpin\Core\Output\OutputInterface;
use Sculpin\Core\Permalink\Permalink;
use Sculpin\Core\Permalink\PermalinkInterface;
use Sculpin\Core\Sculpin;
use Sculpin\Core\Source\MemorySource;
use Sculpin\Core\Source\SourceInterface;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
/**
* Listen for the Sculpin\Core\Sculpin::EVENT_AFTER_RUN event and scan the entire SourceSetEvent space to look for
* pagination artifacts. Then, if artifacts are found, write temporary redirect files to the "old" locations (2.html).
*
* @package Beryllium\Whateverthing
* @author Kevin Boyd - https://whateverthing.com
*/
class LegacyRedirector implements EventSubscriberInterface {
protected $writer;
public function __construct(FilesystemWriter $writer) {
$this->writer = $writer;
}
public static function getSubscribedEvents() {
return [
Sculpin::EVENT_AFTER_RUN => 'onAfterRun',
];
}
public function onAfterRun(SourceSetEvent $event) {
/** @var SourceInterface $source */
foreach ($event->updatedSources() as $source) {
if (!($source instanceof MemorySource)) {
continue;
}
if (false === strpos($source->sourceId(), ':page=')) {
continue;
}
$matches = [];
if (!preg_match('#/page/([0-9]+)$#', $source->permalink()->relativeUrlPath(), $matches)) {
continue;
}
if ($matches[1] === '1') {
continue;
}
$output = $this->buildOutput($source);
$this->writer->write($output);
}
}
public function buildOutput(SourceInterface $source) {
return new class($source) implements OutputInterface {
public $originalPermalink;
public $permalink;
public $source;
public function __construct(SourceInterface $source) {
$this->originalPermalink = $source->permalink();
$this->source = $source;
$this->permalink = new Permalink(
ltrim($source->permalink()->relativeUrlPath(), '/') . '.html',
\dirname($source->permalink()->relativeUrlPath())
);
}
public function outputId(): string {
return $this->source->sourceId() . '_legacy_redirect';
}
public function pathname(): string {
return $this->permalink->relativeFilePath();
}
public function permalink(): PermalinkInterface {
return $this->permalink;
}
public function hasFileReference(): bool {
return false;
}
public function file(): \SplFileInfo {
return null;
}
public function formattedContent(): string {
$redirectUrl = basename($this->originalPermalink->relativeUrlPath());
return <<<EOR
<html><head>
<meta http-equiv="refresh" content="0; URL=$redirectUrl" />
</head><body /></html>
EOR;
}
};
}
}
services:
whateverthing.legacy_redirector:
class: Beryllium\Whateverthing\LegacyRedirector
arguments:
$writer: '@sculpin.writer'
tags:
- 'kernel.event_subscriber'
public: true
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.