.Netcore 2.0 Ocelot Api网关教程(8)- 缓存

Ocelot中使用 CacheManager 来支持缓存,官方文档中强烈建议使用该包作为缓存工具。
以下介绍通过使用CacheManager来实现Ocelot缓存。

1、通过Nuget添加 Ocelot.Cache.CacheManager

在OcelotGetway项目中添加引用:


Add cache package.png

2、修改 Startup 中的 ConfigureServices 方法

修改如下:

services
    .AddOcelot(new ConfigurationBuilder()
    .AddJsonFile("configuration.json")
          .Build())
    .AddConsul()
    .AddCacheManager(x => x.WithDictionaryHandle())
    .AddAdministration("/administration", "secret");

3、修改 WebApiA 添加一个 TimeController 并添加如下代码:

using System;
using Microsoft.AspNetCore.Mvc;

namespace WebApiA.Controllers
{
    [Produces("application/json")]
    [Route("api/[controller]/[action]")]
    public class TimeController : Controller
    {
        [HttpGet]
        public string GetNow()
        {
            return DateTime.Now.ToString("hh:mm:ss");
        }
    }
}

启动WebApiA项目并使用Postman多次请求 http://localhost:5000/api/Time/GetNow

Now1.png

Now2.png

可以看到每次返回的时间不同。

4、修改OcelotGetway项目中的 configuration.json,在 ReRoutes 中添加如下配置:

{
    "DownstreamPathTemplate": "/api/Time/GetNow",
    "DownstreamScheme": "http",
    "DownstreamHostAndPorts": [
      {
        "Host": "localhost",
        "Port": 5001
      }
    ],
    "UpstreamPathTemplate": "/Now",
    "UpstreamHttpMethod": [ "Get" ],
    "FileCacheOptions": {
      "TtlSeconds": 60,
      "Region": "somename"
    }
}

FileCacheOptions 配置做下解释:

  • TtlSeconds: 缓存时间(秒)
  • Region: 缓存区,表示改配置缓存放到哪个区域,可以在配置管理中进行维护,后边将做详细介绍
    用一句话解释改配置:对链接http://localhost:5000/Now使用somename缓存区进行60秒缓存。
    然后启动OcelotGetway项目,使用Postman请求如下:
    Now from cache.gif

    多次请求在一分钟之内得到的返回数据并未发生变化。
    至此,缓存配置完成。

5、使用配置管理清除缓存

配置管理篇中并没有介绍清除缓存api的使用,而是留到了本片来进行介绍。要使用配置管理需要先按照之前的文章进行配置。
以下介绍清除缓存的方法。
使用Postman post请求http://localhost:5000/administration/connect/token如下:

get token.png

得到token。
使用Postman delete请求http://localhost:5000/administration/outputcache/somename并bearer上述得到的token如下:
delete somename token.png

再次请求http://localhost:5000/Now,可以发现与上次请求的返回时间不同。

注意:两次请求http://localhost:5000/Now的时间间隔要控制在60s之内才能看出效果。

6、实现自己的缓存

Ocelot提供了接口可以让我们自己实现缓存处理类,该类要实现 IOcelotCache<CachedResponse>,并且要在 Startup中的 ConfigureServices 方法中的 AddOcelot 之后添加 services.AddSingleton<IOcelotCache<CachedResponse>, MyCache>(); 来注入自己的缓存处理类覆盖Ocelot中默认的缓存处理。
如果需要实现文件缓存需要实现 IOcelotCache<FileConfiguration> 接口并添加相应注入。
提供一个简单版本的缓存处理类(非常不建议生产环境使用):

using System;
using System.Collections.Generic;
using System.Linq;
using Ocelot.Cache;

namespace OcelotGetway
{
    public class MyCache : IOcelotCache<CachedResponse>
    {
        private static Dictionary<string, CacheObj> _cacheObjs = new Dictionary<string, CacheObj>();
        
        public void Add(string key, CachedResponse value, TimeSpan ttl, string region)
        {
            if (!_cacheObjs.ContainsKey($"{region}_{key}"))
            {
                _cacheObjs.Add($"{region}_{key}", new CacheObj()
                {
                    ExpireTime = DateTime.Now.Add(ttl),
                    Response = value
                });
            }
        }

        public CachedResponse Get(string key, string region)
        {
            if (!_cacheObjs.ContainsKey($"{region}_{key}")) return null;
            
            var cacheObj = _cacheObjs[$"{region}_{key}"];
            if (cacheObj != null && cacheObj.ExpireTime >= DateTime.Now)
            {
                return cacheObj.Response;
            }

            _cacheObjs.Remove($"{region}_{key}");
            return null;

        }

        public void ClearRegion(string region)
        {
            var keysToRemove = _cacheObjs.Where(c => c.Key.StartsWith($"{region}_"))
                .Select(c => c.Key)
                .ToList();
            foreach (var key in keysToRemove)
            {
                _cacheObjs.Remove(key);
            }

        }

        public void AddAndDelete(string key, CachedResponse value, TimeSpan ttl, string region)
        {
            if (_cacheObjs.ContainsKey($"{region}_{key}"))
            {
                _cacheObjs.Remove($"{region}_{key}");
            }
            
            _cacheObjs.Add($"{region}_{key}", new CacheObj()
            {
                ExpireTime = DateTime.Now.Add(ttl),
                Response = value
            });
        }
    }

    public class CacheObj
    {
        public DateTime ExpireTime { get; set; }

        public CachedResponse Response { get; set; }
    }
}

源码下载

完,下一篇介绍QoS

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 196,165评论 5 462
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 82,503评论 2 373
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 143,295评论 0 325
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 52,589评论 1 267
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 61,439评论 5 358
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 46,342评论 1 273
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 36,749评论 3 387
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 35,397评论 0 255
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 39,700评论 1 295
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 34,740评论 2 313
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 36,523评论 1 326
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,364评论 3 314
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 37,755评论 3 300
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,024评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,297评论 1 251
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 41,721评论 2 342
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 40,918评论 2 336

推荐阅读更多精彩内容