# monkey-patching

Published articles for monkey-patching.

This is one page of public article previews, not the complete archive. Follow Next page to continue. Summaries are not the original full articles.

## Wrapture: a Python package for monkey patching, testing, and observability

DevFeed: [Wrapture: a Python package for monkey patching, testing, and observability](<https://devfeed.tech/articles/don-t-sleep-on-wrapture-31170.md>)

Original publisher: [Read original article](<https://simonwillison.net/2026/Sep/11/wrapture/>)

Author: Simon Willison

Published: 2026-09-11T13:51:32Z

Content type: opinion

Language: en

Sources: [Simon Willison's Weblog](<https://devfeed.tech/sources/simon-willison-s-weblog.md>)

Topics: [Python](<https://devfeed.tech/topics/python.md>), [Testing](<https://devfeed.tech/topics/testing.md>), [observability](<https://devfeed.tech/topics/observability.md>), [Instrumentation](<https://devfeed.tech/topics/instrumentation.md>), [tracing](<https://devfeed.tech/topics/tracing.md>), [OpenTelemetry](<https://devfeed.tech/topics/opentelemetry.md>), [Flask](<https://devfeed.tech/topics/flask.md>), [jupyterlab](<https://devfeed.tech/topics/jupyterlab.md>)

Tags: [code](<https://devfeed.tech/tags/code.md>), [graham-dumpleton](<https://devfeed.tech/tags/graham-dumpleton.md>), [graham-dumpleton-6](<https://devfeed.tech/tags/graham-dumpleton-6.md>), [how-to](<https://devfeed.tech/tags/how-to.md>), [instrumentation](<https://devfeed.tech/tags/instrumentation.md>), [monkey-patching](<https://devfeed.tech/tags/monkey-patching.md>), [monkey-patching-10](<https://devfeed.tech/tags/monkey-patching-10.md>), [observability](<https://devfeed.tech/tags/observability.md>), [observability-10](<https://devfeed.tech/tags/observability-10.md>), [open-source](<https://devfeed.tech/tags/open-source.md>), [open-source-320](<https://devfeed.tech/tags/open-source-320.md>), [opentelemetry](<https://devfeed.tech/tags/opentelemetry.md>), [python](<https://devfeed.tech/tags/python.md>), [python-1-283](<https://devfeed.tech/tags/python-1-283.md>), [testing](<https://devfeed.tech/tags/testing.md>), [testing-95](<https://devfeed.tech/tags/testing-95.md>), [tracing](<https://devfeed.tech/tags/tracing.md>)

### AI overview

This article reviews wrapture, an alpha Python package by Graham Dumpleton for monkey patching, unit testing, call recording, live and zero-code tracing, timing analysis, and OpenTelemetry export. It highlights tutorials and JupyterLab workshops covering the package and related instrumentation.

### Source excerpt

Graham Dumpleton's new monkey patching package wrapture is shaping up to be an indispensable tool for Python developers. I'm not sure why I've seen so little buzz about it! Graham has been posting new tutorials for it almost daily since the initial release on August 31st. Here's everything he's published so far: Introducing wrapture - a new monkey patching library that serves both testing and observability (think New Relic style tracing) at the same time. Unit testing with wrapture - how to use it for the same kinds of thing as unittest.mock. Recording calls with wrapture - recording method calls as timelines and processing and displaying them as trees. Phased behaviour in wrapture - arranging patched methods to change behavior across multiple calls. Beyond callables in wrapture - monkey patching attributes, dictionaries, generators. Live tracing with wrapture - tracing a live application to see exactly how it works. Zero-code tracing with wrapture - configuring tracing in a separate TOML file without modifying Python code at all. Tracing Flask with wrapture - using the separate wrapture-instrumenation package to instrument a Flask application. That package also provides instrumentation for aiohttp.client, aiohttp.web, django, fastapi, flask, grpc, http.client, httpx, jinja2, requests, sqlalchemy, sqlite3, starlette, urllib.request, urllib3, uvicorn, werkzeug.serving, wsgiref.simple_server, xmlrpc.client, xmlrpc.server. Finding slow code with wrapture - wrapture's tools for recording timing information, both individually and aggregated across multiple calls. OpenTelemetry export in wrapture - exporting traces to OpenTelemetry. Graham also has a set of interactive workshops for wrapture, implemented as JupyterLab notebooks. Wrapture is still alpha software but it's already very usable - especially given you can configure and try it out with a TOML file without modifying any Python code at all. This feels like one of those Swiss Army Knife packages that, once mastered

## Monkey Patch Detection in Ruby

DevFeed: [Monkey Patch Detection in Ruby](<https://devfeed.tech/articles/monkey-patch-detection-in-ruby-39000.md>)

Original publisher: [Read original article](<https://tenderlovemaking.com/2024/10/16/monkey-patch-detection-in-ruby/>)

Published: 2024-10-16T23:13:00Z

Content type: tutorial

Language: en

Sources: [Aaron Patterson](<https://devfeed.tech/sources/aaron-patterson.md>)

Topics: [Ruby](<https://devfeed.tech/topics/ruby.md>), [Optimization](<https://devfeed.tech/topics/optimization.md>), [implementation](<https://devfeed.tech/topics/implementation.md>), [Code](<https://devfeed.tech/topics/code.md>)

Tags: [code](<https://devfeed.tech/tags/code.md>), [implementation](<https://devfeed.tech/tags/implementation.md>), [monkey-patching](<https://devfeed.tech/tags/monkey-patching.md>), [optimization](<https://devfeed.tech/tags/optimization.md>), [ruby](<https://devfeed.tech/tags/ruby.md>)

### AI overview

This article explains how CRuby detects monkey patches to methods involved in optimizations and de-optimizes when a relevant method is redefined. It describes method tables, redefinition checks, global flags, and class bitmap mappings.

### Source excerpt

My last post detailed one way that CRuby will eliminate some intermediate array allocations when using methods like Array#hash and Array#max. Part of the technique hinges on detecting when someone monkey patches array. Today, I thought we'd dive a little bit in to how CRuby detects and de-optimizes itself when these "important" methods get monkey patched. Monkey Patching Problem The optimization in the previous post made the assumption that the implementation Array#max was the original definition (as defined in Ruby itself). But the Ruby language allows us to reopen classes, redefine any methods we want, and that those methods will "just work". For example, if someone were to reopen Array and define a new max method, we would need to respect that monkey patch: class Array def max "hello!" end end puts [1, 2].max # => "hello!" In fact, a monkey patch implementation could mutate the array itself, so we're definitely required to allocate an array in the case that someone added their own max method: class Array def max self << :neat self end end x = [1, 2].max p x # => [1, 2, :neat] So how does CRuby detect that a method has been monkey patched? Method Definition Time Every time a method is defined, an entry is stored in a hash table pointed to by the current class. We call this the "method table", but you'll see it referred to as M_TBL or RCLASS_M_TBL in the code. The key to the hash is simply the method name as an ID type (an integer which represents a Ruby Symbol), and the value of the hash is a method entry structure. If there was already an entry in the table, then we know it's a "redefinition" (a.k.a. "monkey patch"), and we end up calling rb_vm_check_redefinition_opt_method here. rb_vm_check_redefinition_opt_method checks to see if this is a method we "care" about. Methods we "care" about are typically ones where we've made some kind of optimization and we need to deoptimize if someone redefines them. If the redefined method is something we care to detect, then w

## Implementing multimethods in Python

DevFeed: [Implementing multimethods in Python](<https://devfeed.tech/articles/implementing-multimethods-in-python-32133.md>)

Original publisher: [Read original article](<https://adambard.com/blog/implementing-multimethods-in-python/>)

Published: 2014-12-11T00:00:00Z

Content type: tutorial

Language: en

Sources: [Adam Bard](<https://devfeed.tech/sources/adam-bard.md>)

Topics: [Python](<https://devfeed.tech/topics/python.md>), [Clojure](<https://devfeed.tech/topics/clojure.md>), [implementation](<https://devfeed.tech/topics/implementation.md>), [function](<https://devfeed.tech/topics/function.md>)

Tags: [clojure](<https://devfeed.tech/tags/clojure.md>), [code](<https://devfeed.tech/tags/code.md>), [function](<https://devfeed.tech/tags/function.md>), [implementation](<https://devfeed.tech/tags/implementation.md>), [implementing](<https://devfeed.tech/tags/implementing.md>), [library](<https://devfeed.tech/tags/library.md>), [monkey-patching](<https://devfeed.tech/tags/monkey-patching.md>), [production](<https://devfeed.tech/tags/production.md>), [python](<https://devfeed.tech/tags/python.md>), [test](<https://devfeed.tech/tags/test.md>), [use-cases](<https://devfeed.tech/tags/use-cases.md>)

### AI overview

This article explains multimethods in Python as an implementation of multiple dispatch. It contrasts user-defined dispatch on arbitrary values with conventional single dispatch based on an argument's type, and discusses use cases such as reducing nested conditionals, extending existing classes, and dispatching on dictionary keys.

### Source excerpt

In Clojure (and many other languages), a multimethod is an implementation of multiple dispatch as an alternative to single dispatch. Traditionally, if you define several methods with the same name on different classes, the type/class of the first argument (in Python, self, in many other languages implicit) is used to pick which method to call. This is called "single dispatch" because the decision of which method to call is left up to the inferred type of a single argument. Multimethods take the approach of leaving the dispatch up to the user; you can dispatch on any value at all. You just need to supply a function that returns the value on which you wish to dispatch, and a method for each possible value. For certain cases, this is a lot more flexible than single dispatch.

## Ruby and .NET: Comparing Language Features and Developer Communities

DevFeed: [Ruby and .NET: Comparing Language Features and Developer Communities](<https://devfeed.tech/articles/parenthetical-thesis-on-ruby-net-or-irongem-or-whatever-the-kids-call-it-these-days-33376.md>)

Original publisher: [Read original article](<https://timkellogg.me/blog/2011/08/29/parenthetical-thesis-on-rubynet-or>)

Published: 2011-08-29T00:00:00Z

Content type: opinion

Language: en

Sources: [Tim Kellogg](<https://devfeed.tech/sources/tim-kellogg.md>)

Topics: [Ruby](<https://devfeed.tech/topics/ruby.md>), [.NET](<https://devfeed.tech/topics/net.md>), [C#](<https://devfeed.tech/topics/csharp.md>), [F#](<https://devfeed.tech/topics/fsharp.md>), [Python](<https://devfeed.tech/topics/python.md>)

Tags: [c-sharp](<https://devfeed.tech/tags/c-sharp.md>), [expression](<https://devfeed.tech/tags/expression.md>), [extension](<https://devfeed.tech/tags/extension.md>), [f-sharp](<https://devfeed.tech/tags/f-sharp.md>), [linq](<https://devfeed.tech/tags/linq.md>), [mixins](<https://devfeed.tech/tags/mixins.md>), [monkey-patching](<https://devfeed.tech/tags/monkey-patching.md>), [net](<https://devfeed.tech/tags/net.md>), [python](<https://devfeed.tech/tags/python.md>), [ruby](<https://devfeed.tech/tags/ruby.md>), [unit-tests](<https://devfeed.tech/tags/unit-tests.md>)

### AI overview

The author compares Ruby and .NET, highlighting Ruby's mixins, monkey patching, REPL, and blocks alongside C#'s type safety, LINQ, and expression trees. The author concludes that neither platform is inherently better, but prefers the Ruby community.

### Source excerpt

Since college I've always been a huge fan of dynamic languages. I was really into Python for a long time and in the past year or so I've picked up Ruby. It's well known that the open source/dynamic language world has always looked down on the .NET/Java world as some sort of inferior. While having a conversation with a colleague about ruby versus .NET I stumbled on a conclusion.Ruby has some great features like mixins, monkey patching, a REPL. I also love how blocks make closures such an accessible and natural way to program. Ruby makes easy things easy and hard things fun.On the other hand, C# is one of the most beautiful typesafe languages (although F# is gaining favor with me). Linq and expression trees provide functionality that you literally cannot reproduce in dynamic languages (it requires knowledge of types, which dynamic languages theoretically shouldn't care about). With the crazy stuff that people are doing with expression trees (building SQL statements, mapping objects, selecting properties, etc) it makes it hard to say I'd rather be doing ruby.While C# has some analogous ruby constructs (extension methods are kind of like a lesser form of monkey patching), it still suffers from some of the classical faults of static languages (there can be a lot of extra code just to deal with types and to play nicely with the compiler). At the same time, the compiler also writes tests for you (a contract states you will have these methods, yet in ruby you can't ever be completely sure they'll actually be there. Something that you'd have to write unit tests for in ruby).The conclusion I came to was that, at this point in time, there really isn't a compelling reason why ruby is better than .NET or vice versa. Except for one thing - the communities. The ruby community is nearly too much fun. In Boulder, where I live, there are several companies that host regular hackfests. There are also annual ruby conventions where people get together, socialize, and share new ideas. In