-
Notifications
You must be signed in to change notification settings - Fork 478
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #5653 from freenas/default-storage-class
NAS-107517 / 20.10 / Setup default storage class for k8s
- Loading branch information
Showing
5 changed files
with
116 additions
and
3 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,33 @@ | ||
import re | ||
|
||
from middlewared.service import Service | ||
from middlewared.utils import run | ||
|
||
|
||
RE_VENDOR = re.compile(r'description:\s*VGA compatible controller[\s\S]*vendor:\s*(.*)') | ||
|
||
|
||
class DeviceService(Service): | ||
|
||
GPU = None | ||
|
||
async def available_gpu(self): | ||
if self.GPU: | ||
return self.GPU | ||
|
||
not_available = {'available': False, 'vendor': None} | ||
cp = await run(['lshw', '-numeric', '-C', 'display'], check=False) | ||
if cp.returncode: | ||
self.logger.error('Unable to retrieve GPU details: %s', cp.stderr.decode()) | ||
return not_available | ||
|
||
vendor = RE_VENDOR.findall(cp.stdout.decode()) | ||
if not vendor: | ||
self.GPU = not_available | ||
else: | ||
# We only support nvidia based GPU's right now based on equipment available | ||
if 'nvidia' in vendor[0].lower(): | ||
self.GPU = {'available': True, 'vendor': 'NVIDIA'} | ||
else: | ||
self.GPU = not_available | ||
return self.GPU |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
76 changes: 76 additions & 0 deletions
76
src/middlewared/middlewared/plugins/kubernetes_linux/storage_classes.py
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,76 @@ | ||
import os | ||
|
||
from kubernetes_asyncio import client | ||
|
||
from middlewared.service import CallError, CRUDService, filterable | ||
from middlewared.utils import filter_list | ||
|
||
from .k8s import api_client | ||
|
||
|
||
DEFAULT_STORAGE_CLASS = 'openebs-zfspv-default' | ||
|
||
|
||
class KubernetesStorageClassService(CRUDService): | ||
|
||
class Config: | ||
namespace = 'k8s.storage_class' | ||
private = True | ||
|
||
@filterable | ||
async def query(self, filters=None, options=None): | ||
async with api_client() as (api, context): | ||
return filter_list( | ||
[d.to_dict() for d in (await context['storage_api'].list_storage_class()).items], | ||
filters, options | ||
) | ||
|
||
async def do_create(self, data): | ||
async with api_client() as (api, context): | ||
try: | ||
await context['storage_api'].create_storage_class(data) | ||
except client.exceptions.ApiException as e: | ||
raise CallError(f'Failed to create storage class: {e}') | ||
|
||
async def do_update(self, name, data): | ||
async with api_client() as (api, context): | ||
try: | ||
await context['storage_api'].patch_storage_class(name, data) | ||
except client.exceptions.ApiException as e: | ||
raise CallError(f'Failed to create storage class: {e}') | ||
|
||
async def do_delete(self, name): | ||
async with api_client() as (api, context): | ||
try: | ||
await context['storage_api'].delete_storage_class(name) | ||
except client.exceptions.ApiException as e: | ||
raise CallError(f'Failed to delete storage class: {e}') | ||
|
||
async def setup_default_storage_class(self): | ||
try: | ||
await self.setup_default_storage_class_internal() | ||
except Exception as e: | ||
# Let's not make this fatal as workloads managed by us will still be functional | ||
self.logger.error('Failed to setup default storage class: %s', e) | ||
|
||
async def setup_default_storage_class_internal(self): | ||
storage_ds = os.path.join((await self.middleware.call('kubernetes.config'))['dataset'], 'default_volumes') | ||
config = { | ||
'apiVersion': 'storage.k8s.io/v1', | ||
'kind': 'StorageClass', | ||
'metadata': { | ||
'name': DEFAULT_STORAGE_CLASS, | ||
'annotations': {'storageclass.kubernetes.io/is-default-class': 'true'} | ||
}, | ||
'parameters': {'fstype': 'zfs', 'poolname': storage_ds}, | ||
'provisioner': 'zfs.csi.openebs.io', | ||
'allowVolumeExpansion': True, | ||
} | ||
|
||
if await self.query([ | ||
['metadata.annotations.storageclass\\.kubernetes\\.io/is-default-class', '=', 'true'], | ||
['metadata.name', '=', DEFAULT_STORAGE_CLASS], | ||
]): | ||
await self.middleware.call('k8s.storage_class.update', DEFAULT_STORAGE_CLASS, config) | ||
else: | ||
await self.middleware.call('k8s.storage_class.create', config) |