Skip to main content

Design patterns for Python implemented with decorators and classes.

Project description

meta-patterns

Design patterns for Python implemented with decorators and classes.

Getting Started

Currently only one design pattern is implemented: Listener.

Listener Pattern

The Listener pattern (otherwise known as the Observer or Publish-Subscribe pattern) is a behavioral design pattern that lets you define a subscription mechanism to notify multiple objects about any events that happen to the object they’re observing (source).

Its use is demonstrated here:

from metapatterns.listener import Listenable, listenable


class Subject(Listenable):
    @listenable
    def myfunc(self, arg1):
        """
        @listenable indicates this function can be 'listened in on'.
        It allows Listeners to hook into it (see MyListener)
        """
        print("myfunc called with arg", arg1)
        return "Hoozah"

    def myfunc2(self, arg1):
        print("myfunc called with arg", arg1)


class MyListener(Subject.Listener):
    """
    Identify this class as a listener of `Subject` through inheritance.
    This makes it so not all listenable methods need to be implemented (they have a default empty implementation in `Subject.Listener`).
    """
    def on_myfunc(self, arg1):
        print("listened in on call to myfunc with arg", arg1)

    def on_myfunc_finished(self, result, arg1):
        print("listened in on result of myfunc with arg", arg1, "and result", result)

    # This cannot be defined because myfunc2 is not a listenable function in Subject
    #def on_myfunc2(self, arg1):
        #pass

We can run this as follows:

if __name__ == "__main__":
    subject = Subject()
    print("# Calling myfunc without listener")
    subject.myfunc(3)

    listener = MyListener()
    subject.add_listener(listener)

    print("\n# Calling myfunc with listener")
    subject.myfunc(5)

    print("\n# Calling myfunc2 with listener")
    subject.myfunc2(7)

    subject.remove_listener(listener)

    print("\n# Calling myfunc again with listener removed")
    subject.myfunc(5)

which gives the output:

# Calling myfunc without listener
myfunc called with arg 3

# Calling myfunc with listener
listened in on call to myfunc with arg 5
myfunc called with arg 5
listened in on result of myfunc with arg 5 and result Hoozah

# Calling myfunc2 with listener
myfunc called with arg 7

# Calling myfunc again with listener removed
myfunc called with arg 5

Subclassing from Subject.Listener has the advantage of raising a TypeError when an on_ function has no matching counterpart in Subject. This can prevent difficult to solve issues from changing the name of a function in Subject.

Future Work

  • Implement more design patterns.
  • Suggestions? Contact me!

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

meta-patterns-0.1.0.tar.gz (3.8 kB view hashes)

Uploaded Source

Built Distribution

meta_patterns-0.1.0-py3-none-any.whl (4.7 kB view hashes)

Uploaded Python 3

Supported by

AWS AWS Cloud computing and Security Sponsor Datadog Datadog Monitoring Fastly Fastly CDN Google Google Download Analytics Microsoft Microsoft PSF Sponsor Pingdom Pingdom Monitoring Sentry Sentry Error logging StatusPage StatusPage Status page