neutron 的 quota design
发现, cinder, nova 制实现了, CountableResource。 只有nuetron实现了 TrackedResource 和 CountableResource。
I read up the quota of neutron.
http://docs.openstack.org/developer/neutron/devref/quota.html
Let me list the design:
1. Most resources
exposed by the Neutron API are subject to quota limits.
nimble 需要定义 哪些 resources 需要 quota
2. Default values
for quota limits are specified in neutron.conf
conf 可配置。
目前, instance, limite的默认值是多少?
Limits are stored in the Neutron
database; 默认值存DB
Admin users can
override those defaults values on a per-project
basis. Admin用户,可以修改默认值。
Configuration-based
quota management, where every project gets the same quota limit
specified in the configuration file, has been deprecated as of
the Liberty release.
neutron已经废弃了基于configuration 的quota管理,这个对我们没有影响。
3. Quota limits are
enforced at the API layer, before the request is dispatched to
the plugin.
nimble 的quota 也确保在API layer。
4. 不支持 hierarchical multitenancy
Please note that Neutron does not
support both specification of quota limits per user and quota
management for hierarchical multitenancy (as a matter of fact
Neutron does not support hierarchical multitenancy at all).
这个是什么意思?
Also, quota limits are currently not enforced on RPC
interfaces listening on the AMQP bus.
RPC的调用, quota limit 不起作用?
应该是指 RPC的调用 中用到的资源吧?
5. 通过 Quota engine注册测resources 都会受 quota 管理。
Plugin and ML2 drivers are not supposed to enforce quotas
for resources they manage. However, the subnet_allocation [1] extension is an exception
and will be discussed below.
The quota management and enforcement mechanisms discussed
here apply to every resource which has been registered with the
Quota engine, regardless of whether such resource belongs to the
core Neutron API or one of its extensions.
6. quota组件的组成
有两个部分, API 和quota Engine。 Nimble 的设计 是不是需要
quota Engine?
There are two main components in the Neutron quota system:
- The Quota API extension;
- The Quota Engine.
Both components rely on a quota driver. The neutron
codebase currently defines two quota drivers:
- neutron.db.quota.driver.DbQuotaDriver
- neutron.quota.ConfDriver
The latter driver is however deprecated.
The Quota API
extension handles quota management, whereas the Quota Engine
component handles quota enforcement.
API 负责quota的管理, Engine 负责quota的执行。
This API
extension is loaded like any other extension.
For this reason
plugins must explicitly support it by including “quotas” in the
support_extension_aliases attribute.
言外之意, quotas不是必须的。
For a
reservation to be successful, the total amount of resources
requested, plus the total amount of resources reserved, plus the
total amount of resources already stored in the database should
not exceed the project’s quota limit.
quota Engine 看来是有必要的。 管理起来有些负责。
request + reserved +
DB amount <= limit
7. 删除意味着回复默认值
Please note that
the current behaviour when deleting a project quota is to reset
quota limits for that project to configuration defaults.
The API
extension does not validate the project identifier with the
identity service. 不校验 project ID
=======================================================================
http://docs.openstack.org/developer/neutron/devref/quota.html#quota-management
1. quota-management (quota的管理)
The quota management component is fairly straightforward.
However, unlike the vast majority of Neutron extensions,
it uses it own controller class [3]. This class does not implement
the POST operation. List, get, update, and delete
operations are implemented by the usual index, show, update and
delete methods. These method simply call into the quota driver
for either fetching project quotas or updating them.
不支持创建, 所以删除 就是回复默认值。
nimble 是否类似?
The _update_attributes method is called only once in the
controller lifetime. This method dynamically updates Neutron’s
resource attribute map [4] so
that an attribute is added for every resource managed by the
quota engine.
Request authorisation is performed in this controller,
and only ‘admin’ users are
allowed to modify quotas for projects.
目前 只有Admin 有授权。
As the neutron policy engine is not used, it is not possible to configure which users should
be allowed to manage quotas using policy.json.
authorization 机制目前不支持其他的用户 管理
quotas。
The driver operations dealing with quota management are:
- delete_tenant_quota, which
simply removes all entries from the ‘quotas’ table for a
given project identifier;- update_quota_limit, which
adds or updates an entry in the ‘quotas’ project for a
given project identifier and a given resource name;- _get_quotas, which fetches
limits for a set of resource and a given project
identifier- _get_all_quotas, which
behaves like _get_quotas, but for all projects.
http://docs.openstack.org/developer/neutron/devref/quota.html#resource-usage-info
2. quota 中 resource 的使用信息。
Neutron 有2种, resource usage info的跟踪。
Neutron has two ways of tracking resource usage info:
- CountableResource, where
resource usage is calculated every time quotas limits are
enforced by counting rows in the resource table and
reservations for that resource.就是一种 同步机制?, 每次 在check quotas 有没有超限的时候。
- TrackedResource, which
instead relies on a specific table
tracking usage data, and performs explicitly counting only
when the data in this table are not in sync with actual
used and reserved resources.就是一种异步机制?, 数据不一致的时候,
执行一下。 需要在db中 额外加一个 table。
Another difference between CountableResource and
TrackedResource is that the former invokes a plugin method to
count resources. CountableResource should be therefore employed
for plugins which do not leverage the Neutron database. The
actual class that the Neutron quota engine will use is determined by the track_quota_usage variable
in the quota configuration section.
If True, TrackedResource instances will be created, otherwise
the quota engine will use CountableResource instances. Resource
creation is performed by the create_resource_instance factory
method in the neutron.quota.resource module.
这两种
方法可配置 quota configuration section.
From a performance
perspective, having a table tracking resource usage has some
advantages, albeit not fundamental. Indeed the time required for
executing queries to explicitly count objects will increase with
the number of records in the table. On the other hand, using
TrackedResource will fetch a single record, but has the drawback of having to execute an UPDATE
statement once the operation is completed. Nevertheless,
CountableResource instances do not simply perform a SELECT query
on the relevant table for a resource, but invoke a plugin
method, which might execute several statements and sometimes
even interacts with the backend before returning. Resource usage
tracking also becomes important for operational correctness when
coupled with the concept of resource reservation, discussed in
another section of this chapter.
性能上 TrackedResource 更好。
缺点 :
having to execute an UPDATE statement
Tracking quota usage is not as
simple as updating a counter every time resources are
created or deleted. Indeed a quota-limited resource in Neutron
can be created in several ways. While a RESTful API request is
the most common one, resources can be created by RPC handlers
listing on the AMQP bus, such as those which create DHCP ports,
or by plugin operations, such as those which create router
ports.
每次资源的创建(如创建一个ports)/删除, quota usage 跟踪比较麻烦。
估计nimble 也类似。
To this aim, TrackedResource instances are initialised
with a reference to the model class for the resource for which
they track usage data. During object initialisation, SqlAlchemy event handlers are
installed for this class. The event handler is executed after a
record is inserted or deleted. As result usage data for that
resource and will be marked as ‘dirty’ once the operation
completes, so that the next time usage data is requested, it
will be synchronised counting resource usage from the database.
Even if this solution has some drawbacks, listed in the
‘exceptions and caveats’ section, it is more reliable than
solutions such as:
都引入了
SqlAlchemy event handlers, 看来是比较麻烦。
- Updating the usage counters
with the new ‘correct’ value every time an operation
completes.- Having a periodic task
synchronising quota usage data with actual data in the
Neutron DB.
Finally, regardless of whether CountableResource or
TrackedResource is used, the quota engine always invokes its
count() method to retrieve resource usage. Therefore, from the
perspective of the Quota engine there is absolutely no
difference between CountableResource and TrackedResource.
采用 CountableResource 还是
TrackedResource, quotas engine 没有区别, 都是调用同一个函数。
=======================================================================
http://docs.openstack.org/developer/neutron/devref/quota.html#quota-enforcement
看来, quota engine 设计的还是不错, 考虑到了很多 edge case。
1. quota-enforcement (quota的执行)
Before dispatching a request to
the plugin, the Neutron ‘base’ controller [5] attempts
to make a reservation for requested
resource(s). Reservations are made by calling the
make_reservation method in neutron.quota.QuotaEngine. The
process of making a reservation is fairly straightforward:
dispatch
之前,先reserve
- Get current resource
usages. This is achieved by invoking the count method on
every requested resource, and then retrieving the amount
of reserved resources.- Fetch current quota limits
for requested resources, by invoking the
_get_tenant_quotas method.- Fetch expired reservations for
selected resources. This amount will be subtracted from resource usage.
As in most cases there won’t be any expired reservation,
this approach actually requires less DB operations than
doing a sum of non-expired, reserved resources for each
request.还有过期的reservation, 需要从usage中扣掉。
- For each resource
calculate its headroom,
and verify the requested amount of resource is less than
the headroom.headroom, 哈哈, 老外们的词汇丰富啊。
直接使用 “可用的”, available, 更直接。
- If the above is true for
all resource, the reservation is saved in the DB,
otherwise an OverQuotaLimit exception is raised.
The quota
engine is able to make a reservation for multiple resources.
However, it is worth noting that because of the current
structure of the Neutron API layer, there will not be any
practical case in which a reservation for multiple resources
is made. For this reason performance optimisation avoiding
repeating queries for every resource are not part of the
current implementation.
quota
engine 设计的还是很好,支持多resource的reservation。
不过 neutron
API 没有使用。
Nimble需要考虑 多 resource reservation 吗?
In order to ensure correct
operations, a row-level lock is
acquired in the transaction which creates the reservation. The
lock is acquired when reading usage data.
In case of write-set certification
failures, which can occur in active/active clusters
such as MySQL galera, the decorator
neutron.db.api.retry_db_errors will retry
the transaction if a DBDeadLock exception is raised.
创建
reservation的时候, 有 lock 用来避免race。
双活 HA的 write-set
certification failures 都考虑了。 有retry机制
While
non-locking approaches are possible, it has been
found out that, since a non-locking algorithms increases the
chances of collision, the cost of handling a DBDeadlock is
still lower than the cost of retrying the operation when a
collision is detected. A study in this direction was conducted
for IP allocation operations, but the same principles apply
here as well [6]. Nevertheless, moving
away for DB-level locks is something that must happen
for quota enforcement in the future.
看看没有 锁 也是可行的, 然而那是后面的事情了。
Committing and cancelling a
reservation is as simple as deleting the reservation itself.
Committing reservation 流程:
When a reservation is committed,
the resources which were committed are now stored in the
database, so the reservation itself should be deleted.
cancelling reservation 流程:
The Neutron quota engine simply
removes the record when cancelling a reservation (ie: the
request failed to complete), and also marks quota usage info
as dirty when the reservation is
committed (ie: the request completed correctly). Reservations
are committed or cancelled by respectively calling the
commit_reservation and cancel_reservation methods in
neutron.quota.QuotaEngine.
Reservations are not perennial. Eternal reservation would
eventually exhaust projects’ quotas because they would never
be removed when an API worker crashes whilst in the middle of
an operation. Reservation expiration is
currently set to 120 seconds, and is not
configurable, not yet at least. Expired reservations are not
counted when calculating resource usage. While creating a
reservation, if any expired reservation is found, all expired
reservation for that project and resource will be removed from
the database, thus avoiding build-up of expired reservations.
也有生命啊, 真可怜,跟人一样。
默认 120s 到期, 目前不可配置。
nov quota api
这个是nova的quota api 说明
http://developer.openstack.org/api-ref/compute/?expanded=show-server-details-detail,show-a-quota-detail
{
"quota_set": {
"cores": 20,
"fixed_ips": -1,
"floating_ips": 10,
"id": "fake_tenant",
"injected_file_content_bytes": 10240,
"injected_file_path_bytes": 255,
"injected_files": 5,
"instances": 10,
"key_pairs": 100,
"metadata_items": 128,
"ram": 51200,
"security_group_rules": 20,
"security_groups": 10,
"server_groups": 10,
"server_group_members": 10
}
}
inject file 相关的,都是cloud init 或者 config driver 相关的。
不知道, 裸机在deploy阶段, 可不可以 inject file?
fixed_ips, floating_ips 这个裸机有吗?
key_pairs, 我知道MAAS作为裸机管理,是可以注入, key的。 nimble 以后会增加这个功能吗?
metadata security_group
server_groups, nimble 需要吗?
=======================================================================
感觉nimble中, port是需要做quota的。
ironic 没有知道quota
http://developer.openstack.org/api-ref/baremetal/
cinder的 是有的。
http://developer.openstack.org/api-ref/block-storage/v3/?expanded=show-quotas-for-a-user-detail
Name | In | Type | Description |
---|---|---|---|
injected_file_content_bytes | body | integer | The number of bytes of content that are allowed for each injected file. |
metadata_items | body | integer | The number of metadata items that are allowed for each instance. |
reserved (Optional) | body | integer | Reserved volume size. Visible only if you set the usage=true query parameter. |
in_use (Optional) |
body | string | The in use data size. Visible only if you set the usage=true query parameter. |
ram | body | integer | The amount of instance RAM in megabytes that are allowed for each tenant. |
floating_ips | body | integer | The number of floating IP addresses that are allowed for each tenant. |
key_pairs | body | integer | The number of key pairs that are allowed for each user. |
injected_file_path_bytes | body | integer | The number of bytes that are allowed for each injected file path. |
instances | body | integer | The number of instances that are allowed for each tenant. |
security_group_rules (Optional) |
body | integer | The number of rules that are allowed for each security group. |
injected_files | body | integer | The number of injected files that are allowed for each tenant. |
quota_set | body | object | A quota_set object. |
cores | body | integer | The number of instance cores that are allowed for each tenant. |
fixed_ips | body | integer | The number of fixed IP addresses that are allowed for each tenant. Must be equal to or greater than the number of allowed instances. |
id | body | string | The UUID of the volume transfer. |
security_groups | body | integer | The number of security groups that are allowed for each tenant. |
=======================================================================
Setting up
Resource Tracking for a Plugin
By default plugins do not
leverage resource tracking. Having the plugin explicitly
declare which resources should be tracked is a precise design
choice aimed at limiting as much as possible the chance of
introducing errors in existing plugins.
For this reason a plugin must
declare which resource it intends to track. This can be
achieved using the tracked_resources decorator available in
the neutron.quota.resource_registry module. The decorator
should ideally be applied to the plugin’s __init__ method.
The decorator accepts in input a
list of keyword arguments. The name of the argument must be a
resource name, and the value of the argument must be a DB
model class. For example:
- ::
-
- @resource_registry.tracked_resources(network=models_v2.Network,
- port=models_v2.Port,
subnet=models_v2.Subnet,
subnetpool=models_v2.SubnetPool)
Will ensure network, port, subnet
and subnetpool resources are tracked. In theory, it is
possible to use this decorator multiple times, and not
exclusively to __init__ methods. However, this would
eventually lead to code readability and maintainability
problems, so developers are strongly encourage to apply this
decorator exclusively to the plugin’s __init__ method (or any
other method which is called by the plugin only once during
its initialization).
就是必须显示的声明那些resource 需要 track,
调用quota.resource_registry.tracked_resources 就可以了。
可以decorator 多次, 但是不建议这么做。
Notes
for Implementors of RPC Interfaces and RESTful Controllers
Neutron unfortunately does not have a layer which is
called before dispatching the operation from the plugin which
can be leveraged both from RESTful and RPC over AMQP APIs. In
particular the RPC handlers call straight into the plugin,
without doing any request authorisation or quota enforcement.
Therefore RPC handlers must explicitly indicate if they
are going to call the plugin to create or delete any sort of
resources. This is achieved in a simple way, by ensuring
modified resources are marked as dirty after the RPC handler
execution terminates. To this aim developers can use the
mark_resources_dirty decorator available in the module
neutron.quota.resource_registry.
The decorator would scan the whole list of registered
resources, and store the dirty status for their usage trackers
in the database for those resources for which items have been
created or destroyed during the plugin operation.
RPC 调用, 不做任何 授权 和 配额。
所有 如果是 创建或者删除 资源的 RPC, 需要特别 指出。
用 neutron.quota.resource_registry.mark_resources_dirty 装饰一下就可以了。
这个装饰器 会 扫描 注册的resource, 标记发生变化的资源为 dirty 状态。
=======================================================================
quota engine 还存在 局限性 :’(
http://docs.openstack.org/developer/neutron/devref/quota.html#exceptions-and-caveats
Exceptions and Caveats¶
Please be aware of the following limitations of the quota enforcement engine:
- Subnet allocation from subnet
pools, in particularly shared pools, is also subject to quota limit
checks. However this checks are not enforced by the quota engine, but
trough a mechanism implemented in the neutron.ipam.subnetalloc
module. This is because the Quota engine is not able to satisfy the
requirements for quotas on subnet allocation.
哈哈,这是neutron得有的资源, nimble目前不存在这种资源。quota engine 做不了 subnet allocation的 quota 执行。
- The quota engine also provides a
limit_check routine which enforces quota checks without creating
reservations. This way of doing quota enforcement is extremely
unreliable and superseded by the reservation mechanism.
It has not been removed to ensure off-tree plugins and extensions which
leverage are not broken.提供了只check 不创建reservations的 limit_check
routine, 应该是不建议使用了。
- SqlAlchemy events might not be
the most reliable way for detecting changes in resource usage. Since the
event mechanism monitors the data model class, it is paramount for a
correct quota enforcement, that resources are
always created and deleted using object relational mappings. For
instance, deleting a resource with a query.delete call, will not trigger
the event. SQLAlchemy events should be considered as a temporary
measure adopted as Neutron lacks persistent API objects.
原来 SqlAlchemy events
不可靠。只是一个临时方案。
删除的时候,不会触发event。 :’(
Nimble 需要注意一下。
- As
CountableResource instance do not track usage data, when making a
reservation no write-intent lock is acquired. Therefore the quota engine
with CountableResource
is not concurrency-safe.CountableResource
不保证 并发安全
- The mechanism for specifying
for which resources enable usage tracking relies on the fact that the
plugin is loaded before quota-limited resources are registered. For this
reason it is not possible to validate whether
a resource actually exists or not when enabling tracking for it.
Developers should pay particular attention into ensuring resource names
are correctly specified.plugin
在 quota limited resource 注册之前加载,才能使能 resources usage tracking。 没有手段来校验 在使能 track的时候, 资源 是否存在了。这是给码农挖空,犯错误啊。 :’(
nimble 应该不存在这个问题。 让neutron搞plugin, 搞这么复杂。
- The code assumes usage trackers
are a trusted source of truth: if they report a usage counter and the
dirty bit is not set, that counter is correct. If it’s dirty than surely
that counter is out of sync. This is not
very robust, as there might be issues upon restart when toggling the
use_tracked_resources configuration variable, as stale counters might be
trusted upon for making reservations. Also, the same situation might
occur if a server crashes after the API operation
is completed but before the reservation is committed, as the actual
resource usage is changed but the corresponding usage tracker is not
marked as dirty.
trackers 会不robust。
在启动时, 切换 use_tracked_resources
configuration 变量, reservation 可能使用了
陈旧的 usage counter
usage已经改变,但是相应的 usage tracker没有标记为dirty
neutron 的 quota design的更多相关文章
- openstack之neutron配额调整
1. 前言 neutron在安装配置完成之后,openstack为了实现对所有tenant对网络资源的使用,针对neutron设置有专门的配额,以防止租户使用过多的资源,而对其他的tena ...
- Quota Management and Enforcement
Neutron API中大多的resource都需要quota limits. Neutron API暴露出一个extension 来管理quota,Quota limits are enforced ...
- openstack高可用集群21-生产环境高可用openstack集群部署记录
第一篇 集群概述 keepalived + haproxy +Rabbitmq集群+MariaDB Galera高可用集群 部署openstack时使用单个控制节点是非常危险的,这样就意味着单个节 ...
- openstack高可用集群19-linuxbridge结合vxlan
生产环境,假设我们的openstack是公有云,我们一般的linuxbridge结合vlan的模式相对于大量的用户来说是vlan是不够用的,于是我们引进vxlan技术解决云主机内网网络通讯的问题. 我 ...
- Neutron 理解 (4): Neutron OVS OpenFlow 流表 和 L2 Population [Netruon OVS OpenFlow tables + L2 Population]
学习 Neutron 系列文章: (1)Neutron 所实现的虚拟化网络 (2)Neutron OpenvSwitch + VLAN 虚拟网络 (3)Neutron OpenvSwitch + GR ...
- Neutron 理解 (8): Neutron 是如何实现虚机防火墙的 [How Neutron Implements Security Group]
学习 Neutron 系列文章: (1)Neutron 所实现的虚拟化网络 (2)Neutron OpenvSwitch + VLAN 虚拟网络 (3)Neutron OpenvSwitch + GR ...
- Puppet Openstack Mitaka Design Summit小结
Puppet Openstack Design Summit小结 经过Puppet Openstack社区的不断努力,Puppet Openstack社区目前提供的Official Modules已经 ...
- 怎样写 OpenStack Neutron 的 Extension (一)
前两篇文章讨论了怎么写一个 Neutron 的插件.但是最基本的插件只包括 Network, Port,和 Subnet 三种资源.如果需要引入新的资源,比如一个二层的 gateway 的话,就需要在 ...
- Neutron Networking QoS
目前,Neutron有一个QoS的proposal(https://wiki.openstack.org/wiki/Neutron/QoS#Documents),但是只有Ciscso和NVP插件实现了 ...
随机推荐
- 安装Cuda9.0+cudnn7.3.1+tensorflow-gpu1.13.1
我的安装版本: win10 x64 VS2015 conda python 3.7 显卡 GTX 940mx Cuda 9.0 cudnn v7.3.1 Tensorflow-gpu 1.13.1 1 ...
- 答案在哪里?action config/Interceptor/class/servlet
项目已提测,这两天我们都集中精力梳理外包团队给我司研发的这个三方支付系统的代码逻辑.今天下午爱琴海会议室,开发组里一同学分享他对支付结果回调的梳理成果. 支付结果回调的整体时序是:支付渠道方处理完用户 ...
- sqli-labs(十四)(宽字节注入)
数据库使用gbk编码的时候,会将两个字符合并成一个中文. 写在前面吧,对php的代码审计也会有帮助 直接使用 set character_set_client=gbk 或者是常见的mysql_quer ...
- nat123学习笔记
1.NAT123内网映射端口 在无内网路由管理员权限的情况下,需要将内网web应用暴露到公网访问,此时需要用到花生壳或者nat123(两个应用都不是免费的,其中花生壳可以8元认证,以后免费使用,nat ...
- notepad怎么把空格替换成回车?
替换时选中“使用正则表达式”查找里输入\s替换里输入\r然后“全部替换”即可
- Rpgmakermv(24 )yep_coreengine
==左部为原文,右边我做了简要翻译=================================== Introduction and Instructions ================= ...
- Sitecore系统教程之模板理解
Sitecore中的所有内容都是一个项目.模板也是如此.Sitecore中的模板是一个项目,它定义了其他项目的结构和行为.Sitecore中的每个项目都是某个模板的实例.模板还可以定义它分解成的部分和 ...
- [转]LoadRunner 各个指标分析
转载:https://www.cnblogs.com/dvbbs2012/p/4073635.html 我们要监视CPU,内存.硬盘的资源情况.得到以下的参数提供分析的依据.%processor ti ...
- .net中的集合
集合命令空间: 命令空间:类型逻辑上的分类 System.Collections 非泛型集合 System.Collections.Generic 泛型集合 集合内部存数据,实际上都是存到了数组里. ...
- IPERF 网络性能测试
Iperf 是一个网络性能测试工具.Iperf可以测试最大TCP和UDP带宽性能.Iperf具有多种参数和UDP特性,可以根据需要调整.Iperf可以报告带宽,延迟抖动和数据包丢失. Iperf 参数 ...