挂钩 php 中的函数调用

发布于 2024-11-15 11:29:33 字数 288 浏览 1 评论 0原文

一点背景知识:在运行时,我希望能够检查当前调用的函数 javadoc 样式文档,以确定其正式(类型化)声明。这将允许在调试和测试期间通过反射(有代价)进行运行时类型检查(对于简单和复杂类型),我发现这非常有帮助。

因此,在 php 中,我希望每当任何其他函数将被调用时都调用用户定义的函数。也就是说,如果函数 foo() 被调用,我希望在之前调用我的 callHookHandler() 函数。

一种解决方案是在所有用户定义的类中实现 __call() ,但这既笨重又不包括对类外部定义的函数的支持,因此我正在寻找更好的解决方案。

A little background: At runtime I would like to be able to inspect the currently called functions javadoc-style documentation, to determine its formal (typed) declaration. This would allow runtime type checking (for simple and complex types) by means of reflection (at a cost) during debugging and testing, something that I would find immensely helpful.

So, in php I would like for a user defined function to get called whenever any other function is about to get called. That is, if a function foo() gets called, I would like to have my callHookHandler() function called immediately before.

One solution would be to implement __call() in all user defined classes, but that is both unwieldy and doesn't include support for functions defined outside classes, so I am looking for a better solution.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

终难愈 2024-11-22 11:29:33

这听起来有点有趣,所以我将尝试回答它。

我希望这对你有帮助。让我知道进展如何。

因此,您所要求的可以完成,具体方法如下:

对于函数:

  1. 使用$function = get_define_functions()获取所有定义的函数。
  2. 循环遍历 $functions['user'] 键并使用 ReflectionFunction 类检查每个键。您需要获得:
  3. 使用 ->getDocComment() 的注释
  4. 使用 ->getParameters() 的参数
  5. 做一些魔法(我会让你弄清楚如何使用一些正则表达式解析注释并将其与反射中的参数列表相匹配不要忘记可选参数!)
  6. 使用 runkit_function_rename 重命名函数
  7. 在检查参数的字符串中生成代码。并打电话重命名的函数
  8. 将参数列表生成为字符串
  9. 使用您在步骤 #5 中生成的代码和步骤 #6 中的参数列表通过 runkit_function_add 创建一个新函数。

对于类:

  1. 使用 $classes = get_declared_classes(); 获取类列表
  2. 循环遍历每个类并使用 ReflectionObject检查它->getMethods() 获取方法。使用 ->isInternal() 确保该类不是内部类,因为我们无法对内部类执行任何操作。
  3. 在内部循环中...使用 ReflectionMethod 类遍历每个方法。获取参数和 PHPDoc/JavaDoc 注释,就像处理普通函数一样。
  4. 对函数执行相同的操作,仅使用 runkit_method_addrunkit_method_rename 代替。

缺点:

您将无法对内部类方法和函数进行检查(这很好,因为它们无论如何都没有文档注释)。

这是很多工作!我把很多部分留给了你的想象力,以避免这成为一本小书的篇幅。

请发送给我这个或开源它,并在完成后告诉我,我真的很想自己使用它。联系信息位于我的个人资料中的网站上;)

或者:

您可以使用XDebug函数跟踪以及反射,然后在事后分析结果,这样您就不必动态编辑代码。如果您想编写单元测试,您甚至可以将其自动化。

希望类型检查能够进入 PHP 的未来版本并等待: https://wiki.php.net/rfc /typechecking

注释:

这个类参考有一个在页面评论部分解析 docComments 的潜在有用示例:
http://us.php.net/manual/en/class.reflectionmethod。 php

参考

This sounds a bit of a fun one so I'm going to give answering it a try.

I hope this helps you. Let me know how it goes.

So, what you are asking can be done, and here's how:

For Functions:

  1. Get all defined functions with $function = get_defined_functions().
  2. Loop through the $functions['user'] key and inspect each one with the ReflectionFunction class. You'll need to get:
  3. The comment using ->getDocComment()
  4. The arguments using ->getParameters()
  5. Do some magic (I'll let you figure out how to parse the comment using some regular extressions and match it up with the parameter list from the reflection. Don't forget optional parameters!)
  6. Rename the function using runkit_function_rename
  7. Generate code in a string that checks the parameters and calls the renamed function
  8. Generate a parameter list as a string
  9. Create a new function with runkit_function_add using the code you generated in step #5 and the parameter list from step #6.

For Classes:

  1. Get a list of classes with $classes = get_declared_classes();
  2. Loop through each one and inspect it with ReflectionObject and ->getMethods() to get the methods. Make sure that the class is not internal with ->isInternal() because we can't do anything about the internal classes.
  3. In an inner loop... go through each method using the ReflectionMethod class. Get the arguments and PHPDoc/JavaDoc comments just like you did with normal functions.
  4. Do the same thing you did with the functions only use runkit_method_add and runkit_method_rename instead.

Downsides:

You won't be able to do the checking on internal class methods and functions (which is fine because they won't have doc comments anyway).

This is a lot of work! I left a lot of parts up to your imagination to avoid this being the length of a short book.

Please send me this or open source it and let me know when you finish, I really want to use this myself. Contact info is on my website which is in my profile ;)

Alternatively:

You can use XDebug's function trace along with reflection then analyze the results after the fact so that you don't have to dynamically edit the code. If you want to write unit-test you could even automate it.

Hope type checking makes it into future versions of PHP and wait: https://wiki.php.net/rfc/typechecking

Notes:

This class reference has a potentially useful example of parsing docComments in the comments section of the page:
http://us.php.net/manual/en/class.reflectionmethod.php

References

新一帅帅 2024-11-22 11:29:33

挂钩函数调用的另一种方法是使用命名空间的技巧: 在 PHP 中拦截系统函数的执行

你也可以使用 Go!框架定义一个方面来自动拦截系统功能的执行。

Alternative way to hook into function call is to use a trick with namespaces: Intercepting Execution of System Functions in PHP

You can also use the Go! framework to define an aspect to intercept the execution of system functions automatically.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文