A fast Python in-process signal/event dispatching system.

Related tags

Miscellaneousblinker
Overview

Build Status

Blinker

Blinker provides a fast dispatching system that allows any number of interested parties to subscribe to events, or "signals".

Signal receivers can subscribe to specific senders or receive signals sent by any sender.

It supports dispatching to an arbitrary mix of connected coroutines and receiver functions.

>>> from blinker import signal
>>> started = signal('round-started')
>>> def each(round):
...     print "Round %s!" % round
...
>>> started.connect(each)

>>> def round_two(round):
...     print "This is round two."
...
>>> started.connect(round_two, sender=2)

>>> for round in range(1, 4):
...     started.send(round)
...
Round 1!
Round 2!
This is round two.
Round 3!

See the Blinker documentation for more information.

Requirements

Blinker requires Python 2.7, Python 3.4 or higher, or Jython 2.7 or higher.

Changelog Summary

1.3 (July 3, 2013)

  • The global signal stash behind blinker.signal() is now backed by a regular name-to-Signal dictionary. Previously, weak references were held in the mapping and ephemeral usage in code like signal('foo').connect(...) could have surprising program behavior depending on import order of modules.
  • blinker.Namespace is now built on a regular dict. Use blinker.WeakNamespace for the older, weak-referencing behavior.
  • Signal.connect('text-sender') uses an alternate hashing strategy to avoid sharp edges in text identity.

1.2 (October 26, 2011)

  • Added Signal.receiver_connected and Signal.receiver_disconnected per-Signal signals.
  • Deprecated the global 'receiver_connected' signal.
  • Verified Python 3.2 support (no changes needed!)

1.1 (July 21, 2010)

  • Added @signal.connect_via(sender) decorator
  • Added signal.connected_to shorthand name for the temporarily_connected_to context manager.

1.0 (March 28, 2010)

  • Python 3.x compatibility

0.9 (February 26, 2010)

  • Sphinx docs, project website
  • Added with a_signal.temporarily_connected_to(receiver): ... support
Comments
  • Consider asyncio features ala asyncblink

    Consider asyncio features ala asyncblink

    "AsyncBlink is a small extention to Blinker and enables you to use coroutines as receivers for your signals."

    Seems to be essentially a modification of send() like so:

            # the only difference is here. If it's a coroutine,
            # run it with asyncio.async()
            receivers = self.receivers_for(sender) or []
            return_list = []
    
            for receiver in receivers:
                ret = receiver(sender, **kwargs)
                if asyncio.coroutines.iscoroutine(ret):
                    ret = asyncio.async(ret)
                return_list.append((receiver, ret))
    
            return return_list
    

    Useful to have this in Blinker natively? Perhaps something ala:

    def send_async(self, *sender, **kw):
        wrapped = lambda v: asyncio.coroutine(lambda: v)
        values = [(r, wrapped(v)) if asyncio.iscoroutine(v) else (r, v)
                       for r, v in self.send(*sender, **kw)]
        return asyncio.gather(*values)
    

    cc: @jucacrispim

    enhancement 
    opened by jek 22
  • move to github.com/discorporate/blinker

    move to github.com/discorporate/blinker

    @jek iirc you can click somewhere in the settings to move a repo to a new github org.

    guess that is the easiest option to get it there.

    i'ld offer to do some basic maintenance if i get the permissions (like for flatland, including a new pypi release with the new URL).

    opened by ThomasWaldmann 11
  • Speed up send() by 30% when there are no receivers.

    Speed up send() by 30% when there are no receivers.

    Use Cython if exists to speed up the checking if there are receivers. if Cython cant be found it uses a none optimized version.

    A couple of considerations:

    1. Cython module can be marked as required, speeding up all environments. But this is up to you.
    2. The TypeError error raised when more than one sender is given as a param is done AFTER checking the availability of the receivers. it might broken a bit the contract.
    opened by pfreixes 10
  • Drop support for EOL Python

    Drop support for EOL Python

    Fixes https://github.com/jek/blinker/issues/46.

    EOL Python versions are no longer supported by the core Python team and no longer receive security updates.

    image

    https://en.wikipedia.org/wiki/CPython#Version_history

    They're also little used. Here's the pip installs for Blinker from PyPI for last month:

    | python_version | percent | download_count | | -------------- | ------: | -------------: | | 2.7 | 50.71% | 88,260 | | 3.6 | 28.01% | 48,749 | | 3.5 | 14.50% | 25,235 | | 3.4 | 6.41% | 11,153 | | 3.3 | 0.17% | 290 | | 3.7 | 0.13% | 234 | | 2.6 | 0.08% | 131 | | 3.2 | 0.00% | 2 |

    Source: pypinfo --start-date -49 --end-date -22 --percent --pip --markdown Blinker pyversion

    Dropping them eases the maintenance burden and allows more modern features of Python to be used, some of which is included here.

    opened by hugovk 7
  • Replace `\*` with `\\*` in docstrings

    Replace `\*` with `\\*` in docstrings

    For example,

    https://github.com/jek/blinker/blob/b5e9f0629200d2b2f62e13e595b802948bb4fefb/blinker/base.py#L250

    Causes the following deprecation warning.

    DeprecationWarning: invalid escape sequence \*
    

    Here's a reproduction.

    import warnings
    warnings.simplefilter("always")
    x = "\*\*kwargs"
    # <stdin>:1: DeprecationWarning: invalid escape sequence \*
    

    Instead, the \* should be replaced by \\*. The following does not raise a DeprecationWarning.

    import warnings
    warnings.simplefilter("always")
    x = "\\*\\*kwargs"
    

    Not a huge deal, but these warnings pollute my build logs.

    opened by ashwin153 6
  • Continuous Integration

    Continuous Integration

    Hello,

    It will be nice to add Continuous Integration. Please go to https://travis-ci.org/ and enable your blinker project

    add a .travis.yml file with

    language: python
    python:
      - "2.7"
      - "3.2"
      - "3.3"
      - "3.4"
    
    # command to install dependencies
    install:
      - "pip install ."
    
    # command to run tests
    script: nosetests
    

    then you can push your code.

    Kind regards

    opened by femtotrader 4
  • DeprecationWarning: invalid escape sequence \*

    DeprecationWarning: invalid escape sequence \*

    When running pytest on test suite of my work project I have the following warnings at the end of test run:

    .venv/lib/python3.8/site-packages/blinker/base.py:93: 11 warnings
      /usr/lib/publishing/.venv/lib/python3.8/site-packages/blinker/base.py:93: DeprecationWarning: invalid escape sequence \*
        """Connect *receiver* to signal events sent by *sender*.
    
    .venv/lib/python3.8/site-packages/blinker/base.py:161: 11 warnings
      /usr/lib/publishing/.venv/lib/python3.8/site-packages/blinker/base.py:161: DeprecationWarning: invalid escape sequence \*
        """Connect the decorated function as a receiver for *sender*.
    
    .venv/lib/python3.8/site-packages/blinker/base.py:242: 11 warnings
      /usr/lib/publishing/.venv/lib/python3.8/site-packages/blinker/base.py:242: DeprecationWarning: invalid escape sequence \*
        """Emit this signal on behalf of *sender*, passing on \*\*kwargs.
    

    I guess those docstrings should be r"""...""" strings to avoid such warnings. Or \* sequences should be simply replaced by *.

    Deps:

    • CPython 3.8.6
    • pytest 6.1.0
    • blinker 1.4
    opened by decaz 3
  • tox result is strange

    tox result is strange

      py25: commands succeeded  # no python2.5 on my system
      py26: commands succeeded  # no python2.6 on my system
      py27: commands succeeded  # ok
      py30: commands succeeded  # no python3.0 on my system
      py31: commands succeeded  # no python3.1 on my system
      py32: commands succeeded  # no python3.2 on my system
      py33: commands succeeded  # no python3.3 on my system
    ERROR:  py34: InterpreterNotFound: python3.4  # ok
    ERROR:  py35: InterpreterNotFound: python3.5  # ok
      py36: commands succeeded  # ok
    ERROR:  jython: InterpreterNotFound: jython  # ok
    

    So it says "succeeded" although there was no such python interpreter...

    opened by ThomasWaldmann 3
  • @_utilities.lazy_property isn't thread safe

    @_utilities.lazy_property isn't thread safe

    Just thought I'd let u know (from having made this same mistake myself),

    But the application of @_utilities.lazy_property isn't actually thread-safe.

    An example program you can try:

    import threading
    import thread
    
    import time
    
    from blinker import _utilities
    
    
    class SlowThing(object):
    
        @_utilities.lazy_property
        def b(self):
            print "starting reading 'b' thread %s" % thread.get_ident()
            time.sleep(0.5)
            print "finished reading 'b' thread %s" % thread.get_ident()
            return 1
    
    s = SlowThing()
    
    
    def _run():
        s.b
    
    
    threads = []
    for i in range(0, 5):
        t = threading.Thread(target=_run)
        threads.append(t)
        t.start()
    
    
    while threads:
        t = threads.pop()
        t.join()
    
    

    The output of this will create:

    starting reading 'b' thread 140684440516352
    starting reading 'b' thread 140684432123648
    starting reading 'b' thread 140684423730944
    starting reading 'b' thread 140684415338240
    starting reading 'b' thread 140684203915008
    finished reading 'b' thread 140684432123648
    finished reading 'b' thread 140684440516352
    finished reading 'b' thread 140684423730944
    finished reading 'b' thread 140684415338240
    finished reading 'b' thread 140684203915008
    

    So u can see there are many threads at the same time recomputing that property (in this case it doesn't matter, but in other cases it might?)

    Some code that I have made that does appear to work fine:

    Perhaps we can share it somehow...

    https://github.com/openstack/taskflow/blob/master/taskflow/utils/misc.py#L346

    opened by harlowja 3
  • Fixed memory leaks.

    Fixed memory leaks.

    I found a big memory leaks in my project. After studying the problem I have identified the source of the leaks is a dictionaries Signal._by_sender and Signal._by_receiver. I fixed this problem and create the pull request. Please, accept it and release new version of "blinker".

    opened by Cykooz 3
  • get rid of dead snakes

    get rid of dead snakes

    from setup.py / tox.ini:

    [tox]
    envlist = py25,py26,py27,py30,py31,py32,py33,py34,py35,jython
    
              'Programming Language :: Python :: 2',
              'Programming Language :: Python :: 2.4',
              'Programming Language :: Python :: 2.5',
              'Programming Language :: Python :: 2.6',
              'Programming Language :: Python :: 2.7',
              'Programming Language :: Python :: 3',
              'Programming Language :: Python :: 3.0',
              'Programming Language :: Python :: 3.1',
              'Programming Language :: Python :: 3.2',
              'Programming Language :: Python :: 3.3',
              'Programming Language :: Python :: 3.4',
              'Programming Language :: Python :: 3.5',
              'Programming Language :: Python :: 3.6',
    

    Python 2.6 didn't get new releases since 5 years, so I guess for a new blinker release everything older than 2.7 could be dropped.

    The last 3.2 release is also 4y old, so guess all < 3.3 could be dropped (if not even more).

    People still using ancient versions can still use the older blinker release(s).

    Also, tox and setup.py pypi metadata should be kept in sync.

    opened by ThomasWaldmann 2
  • Bump certifi from 2022.6.15 to 2022.12.7 in /docs

    Bump certifi from 2022.6.15 to 2022.12.7 in /docs

    Bumps certifi from 2022.6.15 to 2022.12.7.

    Commits

    Dependabot compatibility score

    Dependabot will resolve any conflicts with this PR as long as you don't alter it yourself. You can also trigger a rebase manually by commenting @dependabot rebase.


    Dependabot commands and options

    You can trigger Dependabot actions by commenting on this PR:

    • @dependabot rebase will rebase this PR
    • @dependabot recreate will recreate this PR, overwriting any edits that have been made to it
    • @dependabot merge will merge this PR after your CI passes on it
    • @dependabot squash and merge will squash and merge this PR after your CI passes on it
    • @dependabot cancel merge will cancel a previously requested merge and block automerging
    • @dependabot reopen will reopen this PR if it is closed
    • @dependabot close will close this PR and stop Dependabot recreating it. You can achieve the same result by closing it manually
    • @dependabot ignore this major version will close this PR and stop Dependabot creating any more for this major version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this minor version will close this PR and stop Dependabot creating any more for this minor version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this dependency will close this PR and stop Dependabot creating any more for this dependency (unless you reopen the PR or upgrade to it yourself)
    • @dependabot use these labels will set the current labels as the default for future PRs for this repo and language
    • @dependabot use these reviewers will set the current reviewers as the default for future PRs for this repo and language
    • @dependabot use these assignees will set the current assignees as the default for future PRs for this repo and language
    • @dependabot use this milestone will set the current milestone as the default for future PRs for this repo and language

    You can disable automated security fix PRs for this repo from the Security Alerts page.

    dependencies 
    opened by dependabot[bot] 0
  • Add a send_async method to the Signal

    Add a send_async method to the Signal

    This allows for signals to send to coroutine receivers by awaiting them. The _async_wrapper and _sync_wrapper allows for conversion of sync and async receivers as required if defined. If not defined a runtime error is raised.

    The wrappers are used to avoid any direct tie into asyncio, trio, greenbacks, asgiref, or other specific async implementation.

    opened by pgjones 4
  • Temporarily disable a signal in a block

    Temporarily disable a signal in a block

    I have an application that generates reports from a bunch of sources. When a report is generated, a Blinker signal report_created is called, and one of the receivers sends an email to subscribers of that report type.

    It sometimes happens, however, that we want to (re/)generate a large amount of reports. In such cases we don’t want email sending to happen. However, if an actual report gets generated meanwhile by the normal means, i want the receiver to be called, so i can’t just disconnect that receiver.

    What i could imagine is something like this:

    with report_created.disable():
        generate_a_lot_of_reports()
    

    As far as i understand, this is not possible in the current Blinker version, but please correct me if i’m wrong. Also, if this use case seems valid (ie. not a unicorn case, when only my project needs it) i’m willing to dig deeper and submit a PR for this.

    opened by gergelypolonkai 1
  • add type hints to the project

    add type hints to the project

    Having type hints for this library would make it possible to check its usage in applications with Mypy. I currently have a work-in-progress of those type hints.

    Before it can be accepted into python/typeshed, I need to get the permission from the maintainers, so is it OK if I submit Blinker stubs to typeshed?

    opened by bbc2 5
Releases(1.5)
  • 1.5(Jul 17, 2022)

    Blinker has moved to Pallets-Eco, an organization for community maintenance of projects related to Pallets, Flask, etc. If you use Blinker and are interested in helping maintain the project, please join us in Discord Chat https://discord.gg/pallets.

    This release fixes some compatibility with Python >= 3.7. Python < 3.7, including 2.7 and Jython, should still work for this release, but will no longer be supported in the next release.

    The documentation has moved to Read the Docs https://blinker.readthedocs.io.

    Source code(tar.gz)
    Source code(zip)
Pydesy package description (EN)

Pydesy package description (EN) Last version: 0.0.2 Geodetic library, which includes the following tasks: 1. Calculation of theodolite traverse (tachy

1 Feb 03, 2022
Automatically load and dump your dataclasses 📂🙋

file dataclasses Installation By default, filedataclasses comes with support for JSON files only. To support other formats like YAML and TOML, filedat

Alon 1 Dec 30, 2021
Fuzz introspector for python

Fuzz introspector High-level goals: Show fuzzing-relevant data about each function in a given project Show reachability of fuzzer(s) Integrate seamles

14 Mar 25, 2022
Repositório contendo atividades no curso de desenvolvimento de sistemas no SENAI

SENAI-DES Este é um repositório contendo as atividades relacionadas ao curso de desenvolvimento de sistemas no SENAI. Se é a primeira vez em contato c

Abe Hidek 4 Dec 06, 2022
Tugas kelompok Struktur Data

Binary-Tree Tugas kelompok Struktur Data Silahkan jika ingin mengubah tipe data pada operasi binary tree *Boleh juga semua program kelompok bisa disat

Usmar manalu 2 Nov 28, 2022
MIB2 STD ZR Firmware Upgrade

Upgrade MIB2 STD ZR Firmware (without Navigation) About This repository contains some scripts and documentation how to upgrade the MIB2 firmware to a

Fabian 18 Dec 29, 2022
Santa's kitchen helper for python

Santa's Kitchen Helper Introduction/Overview Contents UX User Stories Design Wireframes Color Scheme Typography Imagery Features Exisiting Features Fe

Paul Browne 4 May 31, 2022
Rates how pog a word or user is. Not random and does have *some* kind of algorithm to it.

PogRater :D Rates how pogchamp a word is :D A fun project coded by JBYT27 using Python3 Have you ever wondered how pog a word is? Well, congrats, you

an aspirin 2 Jun 25, 2022
Projeto job insights - Projeto avaliativo da Trybe do Bloco 32: Introdução à Python

Termos e acordos Ao iniciar este projeto, você concorda com as diretrizes do Código de Ética e Conduta e do Manual da Pessoa Estudante da Trybe. Boas

Lucas Muffato 1 Dec 09, 2021
Predict if a fuse is usable on an appliance depending on the fuse rating

fuse-feasibility-analysis Predict if a fuse is usable on an appliance depending on the fuse rating , Power rating and resistance in the appliance

Sebastian Muchui 4 Jul 21, 2022
propuestas electorales de los candidatos a constituyentes, Chile 2021

textos-constituyentes propuestas electorales de los candidatos a constituyentes, Chile 2021 Programas descargados desde https://elecciones2021.servel.

Sergio Lucero 6 Nov 19, 2021
XHacks 2021 Startup Track Winner: Be Heard. Educate, Enact, Empower. No voice left behind. (backend)

Be Heard: X Hacks 2021 Submission Educate, Enact, Empower. No voice left behind. Inspiration To say 2020 was an eventful year would be an understateme

3 Jul 14, 2022
A program to generate random numbers b/w 0 to 10 using time

random-num-using-time A program to generate random numbers b/w 0 to 10 using time it uses python's in-built module datetime and an equation which retu

Atul Kushwaha 1 Oct 01, 2022
FantasyBballHelper - Espn Fantasy Basketball Helper

ESPN FANTASY BASKETBALL HELPER The simple goal of this project is to allow fanta

1 Jan 18, 2022
Powerful Assistant

Delta-Assistant Hi I'm Phoenix This project is a smart assistant This is the 1.0 version of this project I am currently working on the third version o

1 Nov 17, 2021
A simple python project which control paint brush in microsoft paint app

Paint Buddy In Python A simple python project which control paint brush in micro

Ordinary Pythoneer 1 Dec 27, 2021
ASCII-Wordle - A port of the game Wordle to terminal emulators/CMD

ASCII-Wordle A 'port' of Wordle to text-based interfaces A near-feature complete

32 Jun 11, 2022
Test pour savoir si je suis capable de paratger une lib avec le monde entier !!

Data analysis Document here the project: MLproject Description: Project Description Data Source: Type of analysis: Please document the project the bet

Lucas_Penarrubia 0 Jan 18, 2022
Multi-Probe Attention for Semantic Indexing

Multi-Probe Attention for Semantic Indexing About This project is developed for the topic of COVID-19 semantic indexing. Directories & files A. The di

Jinghang Gu 1 Dec 18, 2022
Set of tools to analyze Tinynuke samples

tinynuke-toolset You'll find in that repository a set of tools and scripts I developped to analyze Tinynuke samples. Dll extractor: script used to ext

Heat Miser 14 Aug 18, 2022