使用装饰器修补模块中的所有功能

时间:2016-06-24 15:51:03

标签: python

我有一个包含许多函数的python模块,我想为所有这些模块应用一个装饰器。 有没有办法通过猴子修补来修补所有这些,以便为每个函数应用这个装饰器,而无需在应用装饰器的行上进行复制粘贴?

换句话说,我想替换它:

@logging_decorator(args)
func_1():
  pass

@logging_decorator(args)
func_2():
  pass

@logging_decorator(args)
func_3():
  pass


@logging_decorator(args)
func_n():
  pass

有了这个:

patch_func():
  # get all functions of this module
  # apply @logging_decorator to all (or not all) of them

func_1():
  pass

func_2():
  pass

func_3():
  pass

func_n():
  pass

2 个答案:

答案 0 :(得分:3)

我真的不确定这是个好主意。毕竟Explicit is better than implicit

有了这样说,这样的事情应该有效,使用inspect来查找模块的哪些成员可以被装饰,并使用__dict__来操作模块的内容。

import inspect

def decorate_module(module, decorator):
    for name, member in inspect.getmembers(module):
        if inspect.getmodule(member) == module and callable(member):
            if member == decorate_module or member == decorator:
                continue
            module.__dict__[name] = decorator(member)

样本用法:

def simple_logger(f):
    def wrapper(*args, **kwargs):
        print("calling " + f.__name__)
        f(*args, **kwargs)
    return wrapper

def do_something():
    pass

decorate_module(sys.modules[__name__], simple_logger)
do_something()

答案 1 :(得分:1)

我不会很漂亮......但你可以在定义后使用dir()列出所有函数。然后我想不出一种在没有包装函数的情况下修补它们的方法。

import java.util.List;

import net.authorize.Environment;
import net.authorize.api.contract.v1.CreateCustomerPaymentProfileRequest;
import net.authorize.api.contract.v1.CreateCustomerPaymentProfileResponse;
import net.authorize.api.contract.v1.CreditCardType;
import net.authorize.api.contract.v1.CustomerAddressType;
import net.authorize.api.contract.v1.CustomerPaymentProfileType;
import net.authorize.api.contract.v1.MerchantAuthenticationType;
import net.authorize.api.contract.v1.MessageTypeEnum;
import net.authorize.api.contract.v1.MessagesType.Message;
import net.authorize.api.contract.v1.PaymentType;
import net.authorize.api.controller.CreateCustomerPaymentProfileController;
import net.authorize.api.controller.base.ApiOperationBase;

public class CreateCustomerPaymentProfile {
    public static final String apiLoginID= "72mNC7gyq";
    public static final String transactionKey= "**";

    private static final String customerProfileId = "36731856";

    public static void main(String[] args) {
        ApiOperationBase.setEnvironment(Environment.SANDBOX);

        MerchantAuthenticationType merchantAuthenticationType  = new MerchantAuthenticationType() ;
        merchantAuthenticationType.setName(apiLoginID);
        merchantAuthenticationType.setTransactionKey(transactionKey);
        ApiOperationBase.setMerchantAuthentication(merchantAuthenticationType);

        //private String getPaymentDetails(MerchantAuthenticationType merchantAuthentication, String customerprofileId, ValidationModeEnum validationMode) {
        CreateCustomerPaymentProfileRequest apiRequest = new CreateCustomerPaymentProfileRequest();
        apiRequest.setMerchantAuthentication(merchantAuthenticationType);
        apiRequest.setCustomerProfileId(customerProfileId); 

        //customer address
        CustomerAddressType customerAddress = new CustomerAddressType();
        customerAddress.setFirstName("test");
        customerAddress.setLastName("scenario");
        customerAddress.setAddress("123 Main Street");
        customerAddress.setCity("Bellevue");
        customerAddress.setState("WA");
        customerAddress.setZip("98004");
        customerAddress.setCountry("USA");
        customerAddress.setPhoneNumber("000-000-0000");

        //credit card details
        CreditCardType creditCard = new CreditCardType();
        creditCard.setCardNumber("4111111111111111");
        creditCard.setExpirationDate("2023-12");
        creditCard.setCardCode("122");

        CustomerPaymentProfileType profile = new CustomerPaymentProfileType();
        profile.setBillTo(customerAddress);

        PaymentType payment = new PaymentType();
        payment.setCreditCard(creditCard);
        profile.setPayment(payment);

        apiRequest.setPaymentProfile(profile);

        CreateCustomerPaymentProfileController controller = new CreateCustomerPaymentProfileController(apiRequest);
        controller.execute();

        CreateCustomerPaymentProfileResponse response = new CreateCustomerPaymentProfileResponse();
        response = controller.getApiResponse();
        if (response != null) {
            if (response.getMessages().getResultCode() == MessageTypeEnum.OK) {

                System.out.println(response.getCustomerPaymentProfileId());
                System.out.println(response.getMessages().getMessage().get(0).getCode());
                System.out.println(response.getMessages().getMessage().get(0).getText());
                if(response.getValidationDirectResponse() != null)
                    System.out.println(response.getValidationDirectResponse());
            }
            else {
                System.out.println("Failed to create customer payment profile:  " + response.getMessages().getResultCode());
                System.out.println("~~~~ Details Are ~~~~");
                List<Message> messages = response.getMessages().getMessage();
                for (Message message : messages) {
                    System.out.println("Message Code  : "+message.getCode());
                    System.out.println("Message Text  : "+message.getText());
                }
            }
        }
    }
}