//  Copyright(C) 2021. Huawei Technologies Co.,Ltd.  All rights reserved.

// Package limiter implement a token bucket limiter
package limiter

import (
"context"
"huawei.com/npu-exporter/hwlog"
"huawei.com/npu-exporter/utils"
"math"
"net/http"
"time"
)

const (
kilo = 1000.0
)

type limitHandler struct {
concurrency chan struct{}
httpHandler http.Handler
log bool
}

// ServeHTTP implement http.Handler
func (h *limitHandler) ServeHTTP(w http.ResponseWriter, req *http.Request) {
ctx := context.TODO()
reqID := req.Header.Get(hwlog.ReqID.String())
if reqID != "" {
ctx = context.WithValue(context.Background(), hwlog.ReqID, reqID)
}
id := req.Header.Get(hwlog.UserID.String())
if id != "" {
ctx = context.WithValue(ctx, hwlog.UserID, id)
}
path := req.URL.Path
clientIP := utils.ClientIP(req)
clientUserAgent := req.UserAgent()
select {
case _, ok := <-h.concurrency:
if !ok {
return
}
start := time.Now()
h.httpHandler.ServeHTTP(w, req)
stop := time.Since(start)
latency := int(math.Ceil(float64(stop.Nanoseconds()) / kilo / kilo))
if h.log {
hwlog.RunLog.InfofWithCtx(ctx, "%s %s: %s <%3d> (%dms) |%15s |%s ", req.Proto, req.Method, path,
http.StatusOK, latency, clientIP, clientUserAgent)
}
h.concurrency <- struct{}{}
default:
hwlog.RunLog.WarnfWithCtx(ctx, "Reject Request:%s: %s <%3d> |%15s |%s ", req.Method, path,
http.StatusServiceUnavailable, clientIP, clientUserAgent)
http.Error(w, "503 too busy", http.StatusServiceUnavailable)
}
}

// NewLimitHandler new a bucket-token limiter
func NewLimitHandler(maxConcur, maxConcurrency int, handler http.Handler, printLog bool) http.Handler {
if maxConcur < 1 || maxConcur > maxConcurrency {
hwlog.RunLog.Fatal("maxConcurrency parameter error")
}
h := &limitHandler{
concurrency: make(chan struct{}, maxConcur),
httpHandler: handler,
log: printLog,
}
for i := 0; i < maxConcur; i++ {
h.concurrency <- struct{}{}
}
return h
}

hwlog--limiter.go的更多相关文章

  1. Cannot send session cache limiter Cannot modify header information

    当php报出  Cannot send session cache limiter 或Cannot modify header information   的错误时   其理论上是因为php代码以前有 ...

  2. Warning: session_start() [function.session-start]: Cannot send session cache limiter

    Warning: session_start() [function.session-start]: Cannot send session cache limiter - headers alrea ...

  3. go笔记-限速器(limiter)

    参考: https://blog.csdn.net/wdy_yx/article/details/73849713https://www.jianshu.com/p/1ecb513f7632 http ...

  4. ICD2 VPP limiter for new PIC microcontrollers.

    http://www.circuitsathome.com/mcu/pic_vpp_limiter VOUT = 2.5V * ( 1 + 24/10 ) = 2.5 * 3.4 = 8.5V New ...

  5. rate limiter - system design

    1 问题 Whenever you expose a web service / api endpoint, you need to implement a rate limiter to preve ...

  6. 359. Logger Rate Limiter

    /* * 359. Logger Rate Limiter * 2016-7-14 by Mingyang * 很简单的HashMap,不详谈 */ class Logger { HashMap< ...

  7. Rate Limiter

    Whenever you expose a web service / api endpoint, you need to implement a rate limiter to prevent ab ...

  8. RocksDB Rate Limiter源码解析

    这次的项目我们重点关注RocksDB中的一个环节:Rate Limiter.其实Rate Limiter的思想在很多其他系统中也很常用. 在RocksDB中,后台会实时运行compaction和flu ...

  9. 详解FL Studio压缩器——Fruity Limiter(上)

    压缩,是电音制作中重要一步,将声音信号压缩后可过滤噪音并使音质变好.众所周知,音乐编曲软件FL Studio的特色就是电音制作,所以必不可少要用到压缩器,今天我们就用FL Studio20来讲解一下. ...

  10. 详解FL Studio压缩器——Fruity Limiter(下)

    Hello!小伙伴们又见面啦-接上一篇,本篇咱们继续讲解音乐编曲软件FL Studio20压缩器内容. 包络"ENVELOPE"中包含三个旋钮,它们都有什么作用呢?一起来揭晓吧! ...

随机推荐

  1. fastadmin后台分页设置显示方法

    ​ 1.参照日志列表的分页(后台代码都有) 2.修改默认分页配置,在初始化里面加上: pageList: [5,10,'all'], 3.显示列表: [$where, $sort, $order, $ ...

  2. omc.

    OMC 099(4b) D 因为 \((abc)^{\dfrac 13} \le \dfrac{a+b+c}3\)(基本不等式),将 \(a = xy, b = yz, c = xz\) 代入得到 \ ...

  3. ORM增删改查并发性能测试

    这两天在对一些ORM进行性能测试(涉及SqlSugar.FreeSql.Fast.Framework.Dapper.LiteSql),测试用的是Winform程序,别人第一眼看到我的程序,说,你这测试 ...

  4. TDengine概述以及架构模型

    TDengine TDengine是一个高效的存储.查询.分析时序大数据的平台,专为物联网.车联网.工业互联网.运维监测等优化而设计. 您可以像使用关系型数据库MySQL一样来使用它. TDengin ...

  5. 并发原理 — CPU原子性指令(一)

    本篇文章将以Intel CPU作为讨论基础 一.并发的由来 一台计算机有2个cpu,其中CPU1执行程序A,CPU2执行程序B,由于程序A和程序B是两个不同的应用程序,所以它们两个之间并不存在并发问题 ...

  6. 【BotR】CLR类型系统

    .NET运行时之书(Book of the Runtime,简称BotR)是一系列描述.NET运行时的文档,2007年左右在微软内部创建,最初目的是为了帮助其新员工快速上手.NET运行时:随着.NET ...

  7. Logstash:使用ELK堆栈进行API分析

  8. ES小知识点

    elasticsearch.yml配置文件 network.host: _site_ # network.host设置为"_site_",表明它绑定到我们的本地电脑的IP地址 di ...

  9. 设置HTTP请求自动跳转HTTPS

    第一种方式,分两种情况: 第一种情况:修改Nginx安装目录/conf/nginx.conf文件 server { listen 80; server_name localhost; #将localh ...

  10. SQLyog企业版

    一.下载与安装 1.SQLyog的下载 链接:https://www.aliyundrive.com/s/11ZuFqB1z4E提取码:63fu 2.SQLyog的安装 双击下载程序,可以选择默认安装 ...