思考并回答以下问题:
- use Macroable {__call as macroCall;}为什么这样写?
- CacheManager维护了一个[string=>Repository对象]的数组,并管理了各种Cache种类,是一个工厂。怎么理解?
源码
文件结构
Cache门面
Illuminate\Support\Facades\Cache.php
1 |
|
CacheServiceProvider
Illuminate\Cache\CacheServiceProvider.php
1 |
|
工厂
Illuminate\Contracts\Cache\Factory.php
1 |
|
Illuminate\Cache\Repository.php
1 | namespace Illuminate\Cache; |
RedisStore
Illuminate\Cache\RedisStore.php
1 | namespace Illuminate\Cache; |
RedisLock
Illuminate\Cache\Lock.php
1 |
|
Illuminate\Cache\RedisLock
1 |
|
CacheManager
Illuminate\CacheManager.php
1 | namespace Illuminate\Cache; |
缓存
缓存使用
原子锁
注:要使用这个功能,应用必须使用Memcached、Redis缓存驱动作为应用默认的缓存驱动,此外,所有服务器必须和同一台中央缓存服务器进行通信。
原子锁允许你对分布式锁进行操作而不必担心竞争条件,例如,Laravel Forge使用原子锁来确保在一台服务器上同时只有一个远程任务在执行,你可以通过Cache::lock方法来创建和管理锁:
1 | if (Cache::lock('foo', 10)->get()) { |
get方法还可以接收一个闭包,在闭包执行之后,Laravel会自动释放锁:
1 | Cache::lock('foo')->get(function () { |
如果锁在你请求的时候无效,可以告知Laravel等待直到锁有效。如果锁在指定限制时间内无法获取,会抛出Illuminate\Contracts\Cache\LockTimeoutException异常:
1 | use Illuminate\Contracts\Cache\LockTimeoutException; |
管理跨进程的锁
有时候,你可能想要在一个进程中获取锁,在另一个进程中释放锁。例如,你可以在Web请求期间获取锁,然后在该请求触发的某个队列任务最后释放这把锁。在这种场景下,你应该传递锁的域「所有者令牌」到队列任务以便该任务可以使用给定令牌重新实例化锁:
1 | // 在控制器中... |
如果你想要在不管当前所有者的情况下释放锁,可以使用forceRelease方法:1
Cache::lock('foo')->forceRelease();
缓存标签
注:缓存标签目前不支持file或database缓存驱动,此外,当使用多标签的缓存被设置为永久存储时,使用Memcached驱动的缓存有着最佳性能表现,因为Memcached会自动清除陈旧记录。
存储被打上标签的缓存项
缓存标签允许你给相关缓存项打上同一个标签以便于后续清除这些缓存值,被打上标签的缓存可以通过传递一个被排序的标签数组来访问。例如,我们可以通过以下方式在添加缓存的时候设置标签:1
2Cache::tags(['people', 'artists'])->put('John', $john, $seconds);
Cache::tags(['people', 'authors'])->put('Anne', $anne, $seconds);
访问被打上标签的缓存项
要获取被打上标签的缓存项,传递同样的有序标签数组到tags方法然后使用你想要获取的key来调用get方法:
1 | $john = Cache::tags(['people', 'artists'])->get('John'); |
移除被打上标签的数据项
你可以同时清除被打上同一标签/标签列表的所有缓存项,例如,以下语句会移除被打上people或authors标签的所有缓存:
1 | Cache::tags(['people', 'authors'])->flush(); |
这样,上面设置的Anne和John缓存项都会从缓存中移除。
相反,以下语句只移除被打上authors标签的语句,所以只有Anne会被移除而John不会:1
Cache::tags('authors')->flush();
源码
Illuminate\Cache\TaggableStore.php
1 |
|
Illuminate\Cache\TaggedCache.php
1 | namespace Illuminate\Cache; |
Illuminate\Cache\TagSet.php
1 |
|
Illuminate\Cache\RedisTaggedCache.php
1 |
|