Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Convert smb status to api_method #15143

Open
wants to merge 4 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions src/middlewared/middlewared/api/v25_04_0/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@
from .rdma_interface import * # noqa
from .smartctl import * # noqa
from .smb import * # noqa
from .smb_status import * # noqa
from .snmp import * # noqa
from .static_route import * # noqa
from .system_lifecycle import * # noqa
Expand Down
186 changes: 186 additions & 0 deletions src/middlewared/middlewared/api/v25_04_0/smb_status.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,186 @@
from middlewared.api.base import (
BaseModel,
NonEmptyString,
query_result,
)
from pydantic import Field
from typing import Literal
from .common import QueryFilters, QueryOptions

__all__ = ['SmbStatusArgs', 'SmbStatusResult']

EMPTY_STRING = ''
DISABLED = '-'
UNKNOWN = '???'

SmbStatusInformationType = Literal['ALL', 'SESSIONS', 'SHARES', 'LOCKS', 'NOTIFICATIONS']

SmbEncryptionCipher = Literal[DISABLED, 'AES-128-CCM', 'AES-128-GCM', 'AES-256-CCM', 'AES-256-GCM', UNKNOWN]
SmbSigningCipher = Literal[DISABLED, 'HMAC-MD5', 'HMAC-SHA256', 'AES-128-CMAC', 'AES-128-GMAC', UNKNOWN]
SmbCryptoDegree = Literal['none', 'full', 'partial', 'anonymous']


class SmbStatusEncrypt(BaseModel):
cipher: SmbEncryptionCipher
degree: SmbCryptoDegree


class SmbStatusSign(BaseModel):
cipher: SmbSigningCipher
degree: SmbCryptoDegree


class SmbServerId(BaseModel):
pid: NonEmptyString
task_id: NonEmptyString
vnn: NonEmptyString
unique_id: NonEmptyString


class SmbOpenFileShareMode(BaseModel):
hex_str: NonEmptyString = Field(alias='hex')
text: NonEmptyString
READ: bool
WRITE: bool
DELETE: bool


class SmbOpenFileAccessMask(BaseModel):
hex_str: NonEmptyString = Field(alias='hex')
text: NonEmptyString
READ_DATA: bool
WRITE_DATA: bool
APPEND_DATA: bool
READ_EA: bool
WRITE_EA: bool
EXECUTE: bool
READ_ATTRIBUTES: bool
WRITE_ATTRIBUTES: bool
DELETE_CHILD: bool
DELETE: bool
READ_CONTROL: bool
WRITE_DAC: bool
SYNCHRONIZE: bool
ACCESS_SYSTEM_SECURITY: bool


class SmbOpenFileCaching(BaseModel):
hex_str: NonEmptyString = Field(alias='hex')
text: NonEmptyString
READ: bool
WRITE: bool
HANDLE: bool


class SmbOpenFileOplock(BaseModel):
hex_str: NonEmptyString = Field(alias='hex')
text: NonEmptyString
EXCLUSIVE: bool
BATCH: bool
LEVEL_II: bool
LEASE: bool


class SmbOpenFileLease(BaseModel):
lease_key: NonEmptyString
hex_str: NonEmptyString = Field(alias='hex')
text: NonEmptyString
READ: bool
WRITE: bool
HANDLE: bool


class SmbServerChannel(BaseModel):
channel_id: NonEmptyString
creation_time: NonEmptyString
local_address: NonEmptyString
remote_address: NonEmptyString


class SmbOpenFileId(BaseModel):
devid: int
inode: int
extid: int


class ShareEntry:
service: NonEmptyString
server_id: SmbServerId
tcon_id: NonEmptyString
session_id: NonEmptyString
machine: NonEmptyString
connected_at: NonEmptyString
encryption: SmbStatusEncrypt
signing: SmbStatusSign
num_channels: int


class SmbOpenFile(BaseModel):
server_id: SmbServerId
username: NonEmptyString
uid: int
share_file_id: NonEmptyString
sharemode: SmbOpenFileShareMode
access_mask: SmbOpenFileAccessMask
caching: SmbOpenFileCaching
oplock: SmbOpenFileOplock
lease: SmbOpenFileLease
opened_at: NonEmptyString


class LocksEntry(BaseModel):
service_path: NonEmptyString
filename: NonEmptyString
fileid: SmbOpenFileId
num_pending_deletes: int
opens: dict[str, SmbOpenFile]


class SessionsEntry(BaseModel):
session_id: NonEmptyString
server_id: SmbServerId
uid: int
gid: int
username: NonEmptyString
groupname: NonEmptyString
creation_time: NonEmptyString
expiration_time: NonEmptyString
auth_time: NonEmptyString
remote_machine: NonEmptyString
hostname: NonEmptyString
session_dialect: NonEmptyString
client_guid: NonEmptyString
encryption: SmbStatusEncrypt
signing: SmbStatusSign
channels: dict[str, SmbServerChannel]


class AllEntry(SessionsEntry):
share_connections: list[ShareEntry]


class NotificationsEntry(BaseModel):
server_id: SmbServerId
path: NonEmptyString
notification_filter: NonEmptyString = Field(alias='filter')
subdir_filter: NonEmptyString
creation_time: NonEmptyString


class SmbStatusOptions(BaseModel):
verbose: bool = True
fast: bool = False
restrict_user: str = EMPTY_STRING
restrict_session: str = EMPTY_STRING
resolve_uids: bool = True


class SmbStatusArgs(BaseModel):
info_level: SmbStatusInformationType = 'SESSIONS'
query_filters: QueryFilters = Field(alias='query-filters', default=[])
query_options: QueryOptions = Field(alias='query-options', default=QueryOptions())
status_options: SmbStatusOptions = SmbStatusOptions()


class SmbStatusResult(BaseModel):
result: query_result(ShareEntry) | query_result(LocksEntry) | query_result(SessionsEntry) | query_result(NotificationsEntry)
35 changes: 10 additions & 25 deletions src/middlewared/middlewared/plugins/smb_/status.py
Original file line number Diff line number Diff line change
@@ -1,21 +1,24 @@
import enum
import json
import subprocess

from middlewared.api import api_method
from middlewared.api.current import (
SmbStatusArgs, SmbStatusResult,
)

from middlewared.schema import Bool, Dict, Ref, Str
from middlewared.service import Service, accepts
from middlewared.plugins.smb import SMBCmd
from middlewared.service_exception import CallError
from middlewared.utils import filter_list

import enum
import json
import subprocess


class InfoLevel(enum.Enum):
AUTH_LOG = 'l'
ALL = ''
SESSIONS = 'p'
SHARES = 'S'
LOCKS = 'L'
BYTERANGE = 'B'
NOTIFICATIONS = 'N'


Expand All @@ -25,19 +28,7 @@ class Config:
service = 'cifs'
service_verb = 'restart'

@accepts(
Str('info_level', enum=[x.name for x in InfoLevel], default=InfoLevel.ALL.name),
Ref('query-filters'),
Ref('query-options'),
Dict(
'status_options',
Bool('verbose', default=True),
Bool('fast', default=False),
Str('restrict_user', default=''),
Str('restrict_session', default=''),
Bool('resolve_uids', default=True),
), roles=['SHARING_SMB_WRITE', 'READONLY_ADMIN']
)
@api_method(SmbStatusArgs, SmbStatusResult, roles=['SHARING_SMB_WRITE', 'READONLY_ADMIN'])
def status(self, info_level, filters, options, status_options):
"""
Returns SMB server status (sessions, open files, locks, notifications).
Expand All @@ -58,12 +49,6 @@ def status(self, info_level, filters, options, status_options):
this information level will be removed in a future version.
"""
lvl = InfoLevel[info_level]
if lvl == InfoLevel.AUTH_LOG:
return self.middleware.call_sync('audit.query', {
'services': ['SMB'],
'query-filters': filters + [['event', '=', 'AUTHENTICATION']],
'query-options': options
})

"""
Apply some optimizations for case where filter is only asking
Expand Down
Loading