<div dir="ltr"><br><div>







<p class="">Hi manila, I would like to broach the subject of share load balancing.  Currently the share server for an (in this case) NFS share that is newly created is determined at share creation time.  In this proposal, the share server is determined "late binding style" at mount-time instead.</p>
<p class="">For the sake of discussion, lets call the proposed idea "two-level share scheduling".</p>
<p class="">TL;DR remove share server from export_location in database and query the driver for this at mount-time</p><p class=""><br></p>
<p class="">First, a quick description of current behavior:</p>
<p class=""><br></p>
<p class="">When a share is created (from scratch), the manila scheduler identifies a share server from its list of backends and makes an api call to create_share method in the appropriate driver.  The driver executes the required steps and returns the export_location which is then written to the database.</p>
<p class=""><br></p><p class="">For example, this create command:</p>
<p class="">$ manila create --name myshare --share-network fb7ea7de-19fb-4650-b6ac-16f918e66d1d NFS 1</p>
<p class=""><br></p>
<p class="">would result in this </p>
<p class="">$ manila list</p>
<p class="">+--------------------------------------+---------+------+-------------+-----------+-------------+---------------------------------------------------------------+---------------------------------+</p>
<p class="">| ID                                   | Name    | Size | Share Proto | Status    | Volume Type | Export location                                               | Host                            |</p>
<p class="">+--------------------------------------+---------+------+-------------+-----------+-------------+---------------------------------------------------------------+---------------------------------+</p>
<p class="">| 6d6f57f2-3ac5-46c1-ade4-2e9d48776e21 | myshare | 1    | NFS         | available | None        | 10.254.0.3:/shares/share-6d6f57f2-3ac5-46c1-ade4-2e9d48776e21 | jasondevstack@generic1#GENERIC1 |</p>
<p class="">+--------------------------------------+---------+------+-------------+-----------+-------------+---------------------------------------------------------------+---------------------------------+</p>
<p class=""><br></p>
<p class="">with this associated database record:</p>
<p class=""><br></p>
<p class="">mysql> select * from shares\G</p>
<p class="">*************************** 1. row ***************************</p>
<p class="">         created_at: 2015-02-10 07:06:21</p>
<p class="">         updated_at: 2015-02-10 07:07:25</p>
<p class="">         deleted_at: NULL</p>
<p class="">            deleted: False</p>
<p class="">                 id: 6d6f57f2-3ac5-46c1-ade4-2e9d48776e21</p>
<p class="">            user_id: 848b808e91e5462f985b6131f8a905e8</p>
<p class="">         project_id: ed01cbf358f74ff08263f9672b2cdd01</p>
<p class="">               host: jasondevstack@generic1#GENERIC1</p>
<p class="">               size: 1</p>
<p class="">  availability_zone: nova</p>
<p class="">             status: available</p>
<p class="">       scheduled_at: 2015-02-10 07:06:21</p>
<p class="">        launched_at: 2015-02-10 07:07:25</p>
<p class="">      terminated_at: NULL</p>
<p class="">       display_name: myshare</p>
<p class="">display_description: NULL</p>
<p class="">        snapshot_id: NULL</p>
<p class="">   share_network_id: fb7ea7de-19fb-4650-b6ac-16f918e66d1d</p>
<p class="">    share_server_id: c2602adb-0602-4128-9d1c-4024024a069a</p>
<p class="">        share_proto: NFS</p>
<p class="">    export_location: 10.254.0.3:/shares/share-6d6f57f2-3ac5-46c1-ade4-2e9d48776e21</p>
<p class="">     volume_type_id: NULL</p>
<p class="">1 row in set (0.00 sec)</p>
<p class=""><br></p>
<p class=""><br></p>
<p class=""><br></p>
<p class="">Proposed scheme:</p>
<p class="">The proposal is simple in concept.  Instead of the driver (GenericShareDriver for example) returning both share server ip address and path in share export_location, only the path is returned and saved in the database.  The binding of the share server ip address is only determined at share mount time.  In practical terms this means share server is determined by an api call to the driver when _get_shares is called.  The driver would then have the option of determining which IP address from its basket of addresses to return.  In this way, each share mount event presents an opportunity for the NFS traffic to be balanced over all available network endpoints.</p>
<p class="">A possible signature for this new call might look like this (with the GenericShareDriver having the simple implementation of return <span class="">server[</span>'public_address'<span class="">]):</span><br></p>







<p class=""><br></p>
<p class="">    def get_share_server_address(self, ctx, share, share_server):</p>
<p class="">        """Return the IP address of a share server for given share, given current ."""</p>
<p class="">        # implementation dependent logic to determine IP address </p>
<p class="">        address = self._myownloadfilter()</p>
<p class="">        return address</p>
<p class=""><br></p>
<p class=""><br></p>
<p class="">Off the top of my head I see potential uses including:</p>
<p class="">    o balance load over several glusterfs servers</p>
<p class="">    o balance load over several NFS/CIFS share servers which have multiple NICS</p>
<p class="">    o balance load over several generic share servers which are exporting read-only volumes (such as software repositories)</p><p class="">    o i think isilon should also benefit but I will defer to somebody more knowledgable on the subject</p><p class=""><br></p><p class="">I see following cons:</p><p class="">   o slow manila list performance</p><p class="">   o very slow manila list performance if all share drivers are busy doing long operations such as create/delete share</p><p class=""><br></p><p class="">Interested in your thoughts</p><p class="">Jason</p><p class=""><br></p></div></div>