artesaos / seotools
Laravel 和 Lumen 的 SEO 工具
Requires
- php: ^8.1
- ext-json: *
- illuminate/config: ^10.0 || ^11.0
- illuminate/support: ^10.0 || ^11.0
Requires (Dev)
- orchestra/testbench: ^8.0 || ^9.0
- phpspec/phpspec: ~5.1.1 || ^6.0 || ^7.0
- phpunit/phpunit: ^9.0 || ^10.0
- dev-master
- v1.3.1
- v1.3.0
- v1.2.0
- v1.1.0
- v1.0.0
- v0.23.0
- v0.22.1
- v0.22.0
- v0.21.0
- v0.20.2
- v0.20.1
- v0.20.0
- v0.19.1
- v0.19.0
- v0.18.0
- v0.17.2
- v0.17.1
- v0.17.0
- v0.16.0
- v0.15.0
- v0.14.0
- v0.13.0
- v0.12.2
- v0.12.1
- v0.12.0
- v0.11.1
- v0.11.0-beta1
- 0.10.0
- v0.9.2
- v0.9.1
- v0.9.0
- v0.8.2
- v0.8.1
- v0.8.0
- v0.7.4
- v0.7.3.6
- v0.7.3.5
- v0.7.3.4
- v0.7.3.3
- v0.7.3.2
- v0.7.3.1
- v0.7.3
- v0.7.2
- v0.7.1
- v0.6
- 0.4.1
- 0.4
- 0.4-beta
- 0.3-beta
- 0.2-beta
- dev-dev-minor-changes-1
- dev-296-documentation-opengraph-setproduct-missing
- dev-239-jsonldmulti-ability-to-reset-defaultjsonlddata
- dev-98-override-open-graph-default-image
- dev-festure/php8
- dev-analysis-zOMVNR
- dev-analysis-XlKJvr
- dev-analysis-q2Q2Kg
- dev-analysis-XperBZ
- dev-dev-sitemaps
This package is auto-updated.
Last update: 2024-09-20 13:30:38 UTC
README
SEOTools - Laravel 和 Lumen 的 SEO 工具
SEOTools 是一个为 Laravel 5.8+ 和 Lumen 提供一些常见 SEO 技巧辅助器的包。
当前构建状态
统计数据
有关许可证信息,请检查 LICENSE 文件。
功能
- 友好的简单界面
- 设置标题和元标签的简便性
- 为 Twitter Cards 和 Open Graph 设置元标签的简便性
- 设置 JSON Linked Data 的简便性
安装
1 - 依赖关系
第一步是使用 composer 安装包并自动更新您的 composer.json
文件,您可以通过运行以下命令来完成此操作
composer require artesaos/seotools
注意:如果您正在使用 Laravel 5.5,步骤 2 和 3(提供者和别名)是不必要的。SEOTools 支持 Laravel 新的 Package Discovery。
2 - 提供者
您需要更新应用程序配置以注册该包,以便它可以由 Laravel 加载,只需更新您的 config/app.php
文件,在您的 'providers'
部分的末尾添加以下代码
config/app.php
<?php return [ // ... 'providers' => [ Artesaos\SEOTools\Providers\SEOToolsServiceProvider::class, // ... ], // ... ];
Lumen
转到 /bootstrap/app.php
文件并添加此行
<?php // ... $app = new Laravel\Lumen\Application( dirname(__DIR__) ); // ... $app->register(Artesaos\SEOTools\Providers\SEOToolsServiceProvider::class); // ... return $app;
3 - 门面
注意:Lumen 不支持门面。
您可以使用以下门面访问 SEO 工具服务
Artesaos\SEOTools\Facades\SEOMeta
Artesaos\SEOTools\Facades\OpenGraph
Artesaos\SEOTools\Facades\TwitterCard
Artesaos\SEOTools\Facades\JsonLd
Artesaos\SEOTools\Facades\JsonLdMulti
Artesaos\SEOTools\Facades\SEOTools
您可以在您的 config/app.php
文件中为这些门面设置简短的别名。例如
<?php return [ // ... 'aliases' => [ 'SEOMeta' => Artesaos\SEOTools\Facades\SEOMeta::class, 'OpenGraph' => Artesaos\SEOTools\Facades\OpenGraph::class, 'Twitter' => Artesaos\SEOTools\Facades\TwitterCard::class, 'JsonLd' => Artesaos\SEOTools\Facades\JsonLd::class, 'JsonLdMulti' => Artesaos\SEOTools\Facades\JsonLdMulti::class, // or 'SEO' => Artesaos\SEOTools\Facades\SEOTools::class, // ... ], // ... ];
4 配置
发布配置
在您的终端中键入
php artisan vendor:publish
或
php artisan vendor:publish --provider="Artesaos\SEOTools\Providers\SEOToolsServiceProvider"
Lumen 不支持此命令,为此您应将文件
src/resources/config/seotools.php
复制到您的项目的config/seotools.php
在 seotools.php
配置文件中,您可以确定默认值的属性以及一些行为。
seotools.php
- meta
defaults
- 如果未指定页面显示的任何值,则显示的值是什么。如果值为false
,则不显示任何内容。webmaster
- 是否显示主要网站管理工具的标签值。如果为null
,则不显示任何内容。
- opengraph
defaults
- 总是显示的属性,如果没有设置其他值,则替换这些值。 您可以添加原始配置文件中未包含的额外标签。
- twitter
defaults
- 总是显示的属性,如果没有设置其他值,则替换这些值。 您可以添加原始配置文件中未包含的额外标签。
- json-ld
defaults
- 总是显示的属性,如果没有设置其他值,则替换这些值。 您可以添加原始配置文件中未包含的额外标签。
使用方法
Lumen 使用方法
注意:Lumen 不支持门面。
<?php $seotools = app('seotools'); $metatags = app('seotools.metatags'); $twitter = app('seotools.twitter'); $opengraph = app('seotools.opengraph'); $jsonld = app('seotools.json-ld'); $jsonldMulti = app('seotools.json-ld-multi'); // The behavior is the same as the facade echo app('seotools')->generate();
元标签生成器
使用 SEOMeta,您可以创建用于 head
的元标签
Opengraph 标签生成器
使用 OpenGraph,您可以创建用于 head
的 OpenGraph 标签
Twitter 标签生成器
使用 Twitter,您可以创建用于 head
的 OpenGraph 标签
在您的控制器中
<?php namespace App\Http\Controllers; use Artesaos\SEOTools\Facades\SEOMeta; use Artesaos\SEOTools\Facades\OpenGraph; use Artesaos\SEOTools\Facades\TwitterCard; use Artesaos\SEOTools\Facades\JsonLd; // OR with multi use Artesaos\SEOTools\Facades\JsonLdMulti; // OR use Artesaos\SEOTools\Facades\SEOTools; class CommonController extends Controller { public function index() { SEOMeta::setTitle('Home'); SEOMeta::setDescription('This is my page description'); SEOMeta::setCanonical('https://codecasts.com.br/lesson'); OpenGraph::setDescription('This is my page description'); OpenGraph::setTitle('Home'); OpenGraph::setUrl('http://current.url.com'); OpenGraph::addProperty('type', 'articles'); TwitterCard::setTitle('Homepage'); TwitterCard::setSite('@LuizVinicius73'); JsonLd::setTitle('Homepage'); JsonLd::setDescription('This is my page description'); JsonLd::addImage('https://codecasts.com.br/img/logo.jpg'); // OR SEOTools::setTitle('Home'); SEOTools::setDescription('This is my page description'); SEOTools::opengraph()->setUrl('http://current.url.com'); SEOTools::setCanonical('https://codecasts.com.br/lesson'); SEOTools::opengraph()->addProperty('type', 'articles'); SEOTools::twitter()->setSite('@LuizVinicius73'); SEOTools::jsonLd()->addImage('https://codecasts.com.br/img/logo.jpg'); $posts = Post::all(); return view('myindex', compact('posts')); } public function show($id) { $post = Post::find($id); SEOMeta::setTitle($post->title); SEOMeta::setDescription($post->resume); SEOMeta::addMeta('article:published_time', $post->published_date->toW3CString(), 'property'); SEOMeta::addMeta('article:section', $post->category, 'property'); SEOMeta::addKeyword(['key1', 'key2', 'key3']); OpenGraph::setDescription($post->resume); OpenGraph::setTitle($post->title); OpenGraph::setUrl('http://current.url.com'); OpenGraph::addProperty('type', 'article'); OpenGraph::addProperty('locale', 'pt-br'); OpenGraph::addProperty('locale:alternate', ['pt-pt', 'en-us']); OpenGraph::addImage($post->cover->url); OpenGraph::addImage($post->images->list('url')); OpenGraph::addImage(['url' => 'http://image.url.com/cover.jpg', 'size' => 300]); OpenGraph::addImage('http://image.url.com/cover.jpg', ['height' => 300, 'width' => 300]); JsonLd::setTitle($post->title); JsonLd::setDescription($post->resume); JsonLd::setType('Article'); JsonLd::addImage($post->images->list('url')); // OR with multi JsonLdMulti::setTitle($post->title); JsonLdMulti::setDescription($post->resume); JsonLdMulti::setType('Article'); JsonLdMulti::addImage($post->images->list('url')); if(! JsonLdMulti::isEmpty()) { JsonLdMulti::newJsonLd(); JsonLdMulti::setType('WebPage'); JsonLdMulti::setTitle('Page Article - '.$post->title); } // Namespace URI: http://ogp.me/ns/article# // article OpenGraph::setTitle('Article') ->setDescription('Some Article') ->setType('article') ->setArticle([ 'published_time' => 'datetime', 'modified_time' => 'datetime', 'expiration_time' => 'datetime', 'author' => 'profile / array', 'section' => 'string', 'tag' => 'string / array' ]); // Namespace URI: http://ogp.me/ns/book# // book OpenGraph::setTitle('Book') ->setDescription('Some Book') ->setType('book') ->setBook([ 'author' => 'profile / array', 'isbn' => 'string', 'release_date' => 'datetime', 'tag' => 'string / array' ]); // Namespace URI: http://ogp.me/ns/profile# // profile OpenGraph::setTitle('Profile') ->setDescription('Some Person') ->setType('profile') ->setProfile([ 'first_name' => 'string', 'last_name' => 'string', 'username' => 'string', 'gender' => 'enum(male, female)' ]); // Namespace URI: http://ogp.me/ns/music# // music.song OpenGraph::setType('music.song') ->setMusicSong([ 'duration' => 'integer', 'album' => 'array', 'album:disc' => 'integer', 'album:track' => 'integer', 'musician' => 'array' ]); // music.album OpenGraph::setType('music.album') ->setMusicAlbum([ 'song' => 'music.song', 'song:disc' => 'integer', 'song:track' => 'integer', 'musician' => 'profile', 'release_date' => 'datetime' ]); //music.playlist OpenGraph::setType('music.playlist') ->setMusicPlaylist([ 'song' => 'music.song', 'song:disc' => 'integer', 'song:track' => 'integer', 'creator' => 'profile' ]); // music.radio_station OpenGraph::setType('music.radio_station') ->setMusicRadioStation([ 'creator' => 'profile' ]); // Namespace URI: http://ogp.me/ns/video# // video.movie OpenGraph::setType('video.movie') ->setVideoMovie([ 'actor' => 'profile / array', 'actor:role' => 'string', 'director' => 'profile /array', 'writer' => 'profile / array', 'duration' => 'integer', 'release_date' => 'datetime', 'tag' => 'string / array' ]); // video.episode OpenGraph::setType('video.episode') ->setVideoEpisode([ 'actor' => 'profile / array', 'actor:role' => 'string', 'director' => 'profile /array', 'writer' => 'profile / array', 'duration' => 'integer', 'release_date' => 'datetime', 'tag' => 'string / array', 'series' => 'video.tv_show' ]); // video.tv_show OpenGraph::setType('video.tv_show') ->setVideoTVShow([ 'actor' => 'profile / array', 'actor:role' => 'string', 'director' => 'profile /array', 'writer' => 'profile / array', 'duration' => 'integer', 'release_date' => 'datetime', 'tag' => 'string / array' ]); // video.other OpenGraph::setType('video.other') ->setVideoOther([ 'actor' => 'profile / array', 'actor:role' => 'string', 'director' => 'profile /array', 'writer' => 'profile / array', 'duration' => 'integer', 'release_date' => 'datetime', 'tag' => 'string / array' ]); // og:video OpenGraph::addVideo('http://example.com/movie.swf', [ 'secure_url' => 'https://example.com/movie.swf', 'type' => 'application/x-shockwave-flash', 'width' => 400, 'height' => 300 ]); // og:audio OpenGraph::addAudio('http://example.com/sound.mp3', [ 'secure_url' => 'https://secure.example.com/sound.mp3', 'type' => 'audio/mpeg' ]); // og:place OpenGraph::setTitle('Place') ->setDescription('Some Place') ->setType('place') ->setPlace([ 'location:latitude' => 'float', 'location:longitude' => 'float', ]); return view('myshow', compact('post')); } }
SEOTrait
<?php namespace App\Http\Controllers; use Artesaos\SEOTools\Traits\SEOTools as SEOToolsTrait; class CommonController extends Controller { use SEOToolsTrait; public function index() { $this->seo()->setTitle('Home'); $this->seo()->setDescription('This is my page description'); $this->seo()->opengraph()->setUrl('http://current.url.com'); $this->seo()->opengraph()->addProperty('type', 'articles'); $this->seo()->twitter()->setSite('@LuizVinicius73'); $this->seo()->jsonLd()->setType('Article'); $posts = Post::all(); return view('myindex', compact('posts')); } }
在您的视图中
小技巧:传递参数
true
以获取压缩代码并减小文件大小。
<html> <head> {!! SEOMeta::generate() !!} {!! OpenGraph::generate() !!} {!! Twitter::generate() !!} {!! JsonLd::generate() !!} // OR with multi {!! JsonLdMulti::generate() !!} <!-- OR --> {!! SEO::generate() !!} <!-- MINIFIED --> {!! SEO::generate(true) !!} <!-- LUMEN --> {!! app('seotools')->generate() !!} </head> <body> </body> </html>
<html> <head> <title>Title - Over 9000 Thousand!</title> <meta name='description' itemprop='description' content='description...'> <meta name='keywords' content='key1, key2, key3'> <meta property='article:published_time' content='2015-01-31T20:30:11-02:00'> <meta property='article:section' content='news'> <meta property="og:description" content="description..."> <meta property="og:title" content="Title"> <meta property="og:url" content="http://current.url.com"> <meta property="og:type" content="article"> <meta property="og:locale" content="pt-br"> <meta property="og:locale:alternate" content="pt-pt"> <meta property="og:locale:alternate" content="en-us"> <meta property="og:site_name" content="name"> <meta property="og:image" content="http://image.url.com/cover.jpg"> <meta property="og:image" content="http://image.url.com/img1.jpg"> <meta property="og:image" content="http://image.url.com/img2.jpg"> <meta property="og:image" content="http://image.url.com/img3.jpg"> <meta property="og:image:url" content="http://image.url.com/cover.jpg"> <meta property="og:image:size" content="300"> <meta name="twitter:card"content="summary"> <meta name="twitter:title"content="Title"> <meta name="twitter:site"content="@LuizVinicius73"> <script type="application/ld+json">{"@context":"https://schema.org","@type":"Article","name":"Title - Over 9000 Thousand!"}</script> <!-- OR with multi --> <script type="application/ld+json">{"@context":"https://schema.org","@type":"Article","name":"Title - Over 9000 Thousand!"}</script> <script type="application/ld+json">{"@context":"https://schema.org","@type":"WebPage","name":"Title - Over 9000 Thousand!"}</script> </head> <body> </body> </html>
使用宏
在多个地方使用相同的代码会很麻烦,这就是为什么这个包包括一个可宏化的特性。这个特性允许通过简单的特性向未在类定义中定义的类添加额外的功能。
例如,假设您需要为您的页面添加元标题和描述。您可以在 AppServiceProvider 中添加您的宏化函数,或者为这个目的创建一个专门的文件,并像代码片段中所示定义您的函数
SEOTools::macro('webPage', function (string $title, string $description) { SEOMeta::setTitle($title); SEOMeta::setDescription($description); SEOMeta::setCanonical('http://current.url.com'); OpenGraph::setDescription($description); OpenGraph::setTitle($title); OpenGraph::setUrl('http://current.url.com'); OpenGraph::addProperty('type', 'webpage'); });
在您的控制器中,您可以使用以下代码来使用这个函数
SEOTools::webPage('Page title', 'Page description');
API(SEOMeta)
<?php use Artesaos\SEOTools\Facades\SEOMeta; SEOMeta::addKeyword($keyword); SEOMeta::addMeta($meta, $value = null, $name = 'name'); SEOMeta::addAlternateLanguage($lang, $url); SEOMeta::addAlternateLanguages(array $languages); SEOMeta::setAlternateLanguage($lang, $url); SEOMeta::setAlternateLanguages(array $languages); SEOMeta::setTitleSeparator($separator); SEOMeta::setTitle($title); SEOMeta::setTitleDefault($default); SEOMeta::setDescription($description); SEOMeta::setKeywords($keywords); SEOMeta::setRobots($robots); SEOMeta::setCanonical($url); SEOMeta::setPrev($url); SEOMeta::setNext($url); SEOMeta::removeMeta($key); // You can chain methods SEOMeta::setTitle($title) ->setDescription($description) ->setKeywords($keywords) ->addKeyword($keyword) ->addMeta($meta, $value); // Retrieving data SEOMeta::getTitle(); SEOMeta::getTitleSession(); SEOMeta::getTitleSeparator(); SEOMeta::getKeywords(); SEOMeta::getDescription(); SEOMeta::getCanonical($url); SEOMeta::getPrev($url); SEOMeta::getNext($url); SEOMeta::getRobots(); SEOMeta::reset(); SEOMeta::generate();
API(OpenGraph)
<?php use Artesaos\SEOTools\Facades\OpenGraph; OpenGraph::addProperty($key, $value); // value can be string or array OpenGraph::addImage($url); // add image url OpenGraph::addImages($url); // add an array of url images OpenGraph::setTitle($title); // define title OpenGraph::setDescription($description); // define description OpenGraph::setUrl($url); // define url OpenGraph::setSiteName($name); //define site_name // You can chain methods OpenGraph::addProperty($key, $value) ->addImage($url) ->addImages($url) ->setTitle($title) ->setDescription($description) ->setUrl($url) ->setSiteName($name); // Generate html tags OpenGraph::generate();
API(TwitterCard)
<?php use Artesaos\SEOTools\Facades\TwitterCard; TwitterCard::addValue($key, $value); // value can be string or array TwitterCard::setType($type); // type of twitter card tag TwitterCard::setTitle($type); // title of twitter card tag TwitterCard::setSite($type); // site of twitter card tag TwitterCard::setDescription($type); // description of twitter card tag TwitterCard::setUrl($type); // url of twitter card tag TwitterCard::setImage($url); // add image url // You can chain methods TwitterCard::addValue($key, $value) ->setType($type) ->setImage($url) ->setTitle($title) ->setDescription($description) ->setUrl($url) ->setSite($name); // Generate html tags TwitterCard::generate();
API(JsonLd)
<?php use Artesaos\SEOTools\Facades\JsonLd; JsonLd::addValue($key, $value); // value can be string or array JsonLd::setType($type); // type of twitter card tag JsonLd::setTitle($type); // title of twitter card tag JsonLd::setSite($type); // site of twitter card tag JsonLd::setDescription($type); // description of twitter card tag JsonLd::setUrl($type); // url of twitter card tag JsonLd::setImage($url); // add image url // You can chain methods JsonLd::addValue($key, $value) ->setType($type) ->setImage($url) ->setTitle($title) ->setDescription($description) ->setUrl($url) ->setSite($name); // Generate html tags JsonLd::generate();
API(JsonLdMulti)
<?php use Artesaos\SEOTools\Facades\JsonLdMulti; JsonLdMulti::newJsonLd(); // create a new JsonLd group JsonLdMulti::isEmpty(); // check if the current JsonLd group is empty JsonLdMulti::select($index); // choose the JsonLd group that will be edited by the methods below JsonLdMulti::addValue($key, $value); // value can be string or array JsonLdMulti::setType($type); // type of twitter card tag JsonLdMulti::setTitle($type); // title of twitter card tag JsonLdMulti::setSite($type); // site of twitter card tag JsonLdMulti::setDescription($type); // description of twitter card tag JsonLdMulti::setUrl($type); // url of twitter card tag JsonLdMulti::setImage($url); // add image url // You can chain methods JsonLdMulti::addValue($key, $value) ->setType($type) ->setImage($url) ->setTitle($title) ->setDescription($description) ->setUrl($url) ->setSite($name); // You can add an other group if(! JsonLdMulti::isEmpty()) { JsonLdMulti::newJsonLd() ->setType($type) ->setImage($url) ->setTitle($title) ->setDescription($description) ->setUrl($url) ->setSite($name); } // Generate html tags JsonLdMulti::generate(); // You will have retrieve <script content="application/ld+json"/>
API(SEO)
简化对所有 SEO 提供程序的访问
<?php use Artesaos\SEOTools\Facades\SEOTools; SEOTools::metatags(); SEOTools::twitter(); SEOTools::opengraph(); SEOTools::jsonLd(); SEOTools::setTitle($title); SEOTools::getTitle($session = false); SEOTools::setDescription($description); SEOTools::setCanonical($url); SEOTools::addImages($urls);
缺少的功能
有许多与 SEO 相关的功能,您可能需要这些功能来完成您的项目。虽然这个包提供了对基本功能的支持,但其他功能超出了其范围。您需要使用其他包来集成它们。
网站地图
这个包不支持生成网站地图文件。请考虑使用以下包之一来实现这个功能:
URL 尾随斜杠
这个包不处理 URL 的一致性,无论是否存在尾随斜杠符号。如果您需要它,请考虑使用以下包之一:
微数据标记
这个包提供了生成 微数据 HTML 标记 的功能。如果您需要创建以下类似的 HTML
<div itemscope> <p>My name is <span itemprop="name">Elizabeth</span>.</p> </div>
您需要自行处理。
注意:如今,微数据标记被认为已经过时。建议使用 JSON 连接数据 代替,该扩展支持 JSON 连接数据。
RSS
这个包不支持生成 RSS 源或相关元数据组合。请考虑使用以下包之一来实现这个功能: