2016-02-16 85 views
0

我有一個功能界面到後臺庫,它看起來像這樣:重構功能接口

def func1(*pars, **kwargs): 
    be = Backend(...) 
    result = be.do_something(...) 
    result = adapt(result) 
    ... 
    return result 

後端接口已經改變了一點(需要新的config參數),所以現在我需要重構的東西,如:

def func1(config, *pars, **kwargs): 
    be = Backend(config, ...) 
    result = be.do_something(...) 
    result = adapt(result) 
    ... 
    return result 

我需要改變我的接口來接受和傳遞這個新config參數的所有功能。你有關於如何使用這個重構進行更好的建議,使:

  • 最小變動
  • 可以更容易的將來重構,其中可以通過後端

需要多個參數一般來說,你是否有一些關於如何在python中提供乾淨的函數接口的指針?

+1

'config'只能被'Backend'使用嗎? 「後端」是否依賴於其他參數?如果是和不,注入後端而不是配置。 – poke

+0

@poke:這是一個有趣的想法,但我不願意將'Backend'依賴關係推送到上層:我的django層使用'interface',它在內部*使用'Backend'。 – dangonfast

回答

0

嗯,我想你會需要更新你的每一個函數,不管怎樣,但是你可以通過一種方式來實現,這將使未來的更新變得更容易。請看下面的裝飾:

def backend_wrapper(function): 
    def _wrapper(arg1, arg2, arg3, *pargs, **kwargs): 
     backend_args = (arg1, arg2, arg3) 
     return function(backend_args, *pargs, **kwargs) 
    return _wrapper 

如果你更新你的所有功能,使用此裝飾,並接受一個新的位置參數backend_args,那麼你就可以將所有未來的更新,只是裝飾。

class Backend: 
    def __init__(self, *args): 
     print 'Backend args: {}'.format(args) 

@backend_wrapper 
def func1(backend_args, *pargs, **kwargs): 
    be = Backend(*backend_args) 
    print 'Positional args: {}'.format(pargs) 
    print 'Keyword args: {}'.format(kwargs) 

func1('arg1', 'arg2', 'arg3', 'parg1', kwarg1='kwarg1') 
# Backend args: ('arg1', 'arg2', 'arg3') 
# Positional args: ('parg1',) 
# Keyword args: {'kwarg1': 'kwarg1'} 

所以,現在如果我們改變裝飾是:

def backend_wrapper(function): 
    def _wrapper(arg1, *pargs, **kwargs): 
     backend_args = (arg1,) 
     return function(backend_args, *pargs, **kwargs) 
    return _wrapper 

然後,如預期func1仍將運行。

func1('arg1', 'parg1', kwarg1='kwarg1') 
# Backend args: ('arg1',) 
# Positional args: ('parg1',) 
# Keyword args: {'kwarg1': 'kwarg1'} 

這裏的問題是,你仍然需要更新你的函數調用來傳入新的參數。除非你能夠做出全局變量,否則我看不到解決辦法。但是,如果是這樣的話,你可以使用類似:

class Backend: 
    def __init__(self, *args): 
     print 'Backend args: {}'.format(args) 

def backendFactory(*backend_args): 
    def _wrapper(): 
     return Backend(*backend_args) 
    return _wrapper 

def func1(*pargs, **kwargs): 
    be = BackendFactory() 
    print 'Positional args: {}'.format(pargs) 
    print 'Keyword args: {}'.format(kwargs) 

BackendFactory = backendFactory('arg1', 'arg2', 'arg3') 
func1('parg1', kwarg1='kwarg1') 
# Backend args: ('arg1', 'arg2', 'arg3') 
# Positional args: ('parg1',) 
# Keyword args: {'kwarg1': 'kwarg1'} 

這將創建一個全局變量BackendFactory以類似的方式起作用的一類,只不過它存儲的實例變量。請注意,這是混亂和危險的,因爲它答覆你定義一個全局變量,然後在你的函數中使用。