Независимо от того, что вы делаете, убедитесь, что вы не доверяете данным, отправленным с клиента. $_SERVER['REMOTE_ADDR']
содержит реальный IP-адрес соединительной стороны. Это самое надежное значение, которое вы можете найти.
Однако они могут находиться за прокси-сервером, и в этом случае прокси-сервер может установить $_SERVER['HTTP_X_FORWARDED_FOR']
, но это значение легко подделать. Например, он может быть установлен кем-то без прокси, или IP может быть внутренним IP-адресом из локальной сети за прокси-сервером.
Это означает, что если вы собираетесь сохранить $_SERVER['HTTP_X_FORWARDED_FOR']
, сделайте убедитесь, что вы также сохранили значение $_SERVER['REMOTE_ADDR']
. Например. сохраняя оба значения в разных полях в вашей базе данных.
Если вы собираетесь сохранить IP-адрес в базе данных в виде строки, убедитесь, что у вас есть место для не менее 45 символов. IPv6 находится здесь, чтобы остаться, и эти адреса больше, чем старые IPv4-адреса.
(Обратите внимание, что IPv6 обычно использует не более 39 символов, но есть также специальный IPv6 нотация для IPv4-адресов , которая в полной форме может содержать до 45 символов. Поэтому, если вы знаете, что делаете, вы можете использовать 39 символов, но если вы просто хотите установить и забыть, используйте 45).
funcdict = {
'mypackage.mymodule.myfunction': mypackage.mymodule.myfunction,
....
}
funcdict[myvar](parameter1, parameter2)
Почему бы не сохранить функцию самостоятельно? myvar = mypackage.mymodule.myfunction
намного чище.
modname, funcname = myvar.rsplit('.', 1)
getattr(sys.modules[modname], funcname)(parameter1, parameter2)
def f(a,b):
return a+b
xx = 'f'
print eval('%s(%s,%s)'%(xx,2,3))
OUTPUT
5
У меня возникла аналогичная проблема при создании библиотеки для проверки подлинности. Я хочу, чтобы владелец приложения, используя мою библиотеку, мог зарегистрировать обратный вызов с библиотекой для проверки авторизации в отношении групп LDAP, в которых находится аутентифицированный человек. Конфигурация передается как файл config.py, который импортируется и содержит dict с все параметры конфигурации.
Я получил это для работы:
>>> class MyClass(object):
... def target_func(self):
... print "made it!"
...
... def __init__(self,config):
... self.config = config
... self.config['funcname'] = getattr(self,self.config['funcname'])
... self.config['funcname']()
...
>>> instance = MyClass({'funcname':'target_func'})
made it!
Есть ли способ pythonic-er для этого?
Самый простой
eval(myvar)(parameter1, parameter2)
У вас нет функции «указатель». У вас есть функция «name».
Пока это работает хорошо, у вас будет большое количество людей, говорящих вам, что это «небезопасно» или «риск для безопасности».
eval(compile(myvar,'<str>','eval'))(myargs)
compile (..., 'eval') допускает только один оператор, поэтому после вызова не может быть произвольных команд, или будет SyntaxError. Тогда крошечный бит валидации может, по крайней мере, ограничить выражение чем-то в вашей власти, например, начать тестирование «mypackage».
Гораздо лучше иметь возможность просто сохранить функцию, поскольку они являются первоклассными объектами в python.
import mypackage
myfunc = mypackage.mymodule.myfunction
myfunc(parameter1, parameter2)
Но если вам нужно импортировать пакет динамически, тогда вы может достичь этого через:
mypackage = __import__('mypackage')
mymodule = getattr(mypackage, 'mymodule')
myfunction = getattr(mymodule, 'myfunction')
myfunction(parameter1, parameter2)
Помните, однако, что вся эта работа применима к любой области, в которой вы сейчас находитесь. Если вы не будете их упорствовать, вы не можете рассчитывать на они остаются рядом, если вы покинете местность.