Skip to content

Commit

Permalink
Documentation update for 4.1.0 (#1434)
Browse files Browse the repository at this point in the history
* Quick pass through all interface docs

* Move plugin and virtual interface docs up

* Minor doc spring cleaning

* Update readme to include basic installation

* Remove (mostly unused) mailing list from the readme

* Include TRC section in listener docs

* Fix broken links to virtual interfaces

* Add to changelog

* Refactor api docs

* Fix bug in bus example

* Doc updates after review
  • Loading branch information
hardbyte committed Nov 16, 2022
1 parent 2d6e996 commit 2e2f157
Show file tree
Hide file tree
Showing 38 changed files with 486 additions and 365 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@ Features
xlFlushReceiveQueue to xldriver (#1387).
* Vector: Raise a CanInitializationError, if the CAN settings can not
be applied according to the arguments of ``VectorBus.__init__`` (#1426).
* Ixxat bus now implements BusState api and detects errors (#1141)

Bug Fixes
---------
Expand Down
9 changes: 4 additions & 5 deletions README.rst
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ Library Version Python
------------------------------ -----------
2.x 2.6+, 3.4+
3.x 2.7+, 3.5+
4.x *(currently on develop)* 3.7+
4.x 3.7+
============================== ===========


Expand All @@ -74,7 +74,7 @@ Features
- receiving, sending, and periodically sending messages
- normal and extended arbitration IDs
- `CAN FD <https://en.wikipedia.org/wiki/CAN_FD>`__ support
- many different loggers and readers supporting playback: ASC (CANalyzer format), BLF (Binary Logging Format by Vector), CSV, SQLite and Canutils log
- many different loggers and readers supporting playback: ASC (CANalyzer format), BLF (Binary Logging Format by Vector), TRC, CSV, SQLite, and Canutils log
- efficient in-kernel or in-hardware filtering of messages on supported interfaces
- bus configuration reading from a file or from environment variables
- command line tools for working with CAN buses (see the `docs <https://python-can.readthedocs.io/en/stable/scripts.html>`__)
Expand All @@ -84,6 +84,8 @@ Features
Example usage
-------------

``pip install python-can``

.. code:: python
# import the library
Expand Down Expand Up @@ -117,9 +119,6 @@ Discussion
If you run into bugs, you can file them in our
`issue tracker <https://github.com/hardbyte/python-can/issues>`__ on GitHub.

There is also a `python-can <https://groups.google.com/forum/#!forum/python-can>`__
mailing list for development discussion.

`Stackoverflow <https://stackoverflow.com/questions/tagged/can+python>`__ has several
questions and answers tagged with ``python+can``.

Expand Down
2 changes: 1 addition & 1 deletion can/interfaces/cantact.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@
except ImportError:
cantact = None
logger.warning(
"The CANtact module is not installed. Install it using `python -m pip install cantact`"
"The CANtact module is not installed. Install it using `pip install cantact`"
)


Expand Down
2 changes: 1 addition & 1 deletion can/interfaces/udp_multicast/bus.py
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@ class UdpMulticastBus(BusABC):
.. warning::
This interface does not make guarantees on reliable delivery and message ordering, and also does not
implement rate limiting or ID arbitration/prioritization under high loads. Please refer to the section
:ref:`other_virtual_interfaces` for more information on this and a comparison to alternatives.
:ref:`virtual_interfaces_doc` for more information on this and a comparison to alternatives.
:param channel: A multicast IPv4 address (in `224.0.0.0/4`) or an IPv6 address (in `ff00::/8`).
This defines which version of IP is used. See
Expand Down
2 changes: 1 addition & 1 deletion can/interfaces/virtual.py
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ class VirtualBus(BusABC):
.. warning::
This interface guarantees reliable delivery and message ordering, but does *not* implement rate
limiting or ID arbitration/prioritization under high loads. Please refer to the section
:ref:`other_virtual_interfaces` for more information on this and a comparison to alternatives.
:ref:`virtual_interfaces_doc` for more information on this and a comparison to alternatives.
"""

def __init__(
Expand Down
28 changes: 2 additions & 26 deletions doc/api.rst
Original file line number Diff line number Diff line change
Expand Up @@ -17,33 +17,9 @@ A form of CAN interface is also required.
listeners
asyncio
bcm
errors
bit_timing
utils
internal-api


Utilities
---------


.. autofunction:: can.detect_available_configs


.. _notifier:

Notifier
--------

The Notifier object is used as a message distributor for a bus. Notifier creates a thread to read messages from the bus and distributes them to listeners.

.. autoclass:: can.Notifier
:members:


.. _errors:

Errors
------

.. automodule:: can.exceptions
:members:
:show-inheritance:
65 changes: 43 additions & 22 deletions doc/bus.rst
Original file line number Diff line number Diff line change
Expand Up @@ -3,48 +3,55 @@
Bus
---

The :class:`~can.BusABC` class, as the name suggests, provides an abstraction of a CAN bus.
The bus provides a wrapper around a physical or virtual CAN Bus.
An interface specific instance of the :class:`~can.BusABC` is created by the :class:`~can.Bus`
class, for example::
The :class:`~can.Bus` provides a wrapper around a physical or virtual CAN Bus.

An interface specific instance is created by instantiating the :class:`~can.Bus`
class with a particular ``interface``, for example::

vector_bus = can.Bus(interface='vector', ...)

That bus is then able to handle the interface specific software/hardware interactions
and implements the :class:`~can.BusABC` API.
The created bus is then able to handle the interface specific software/hardware interactions
while giving the user the same top level API.

A thread safe bus wrapper is also available, see `Thread safe bus`_.

.. autoclass:: can.Bus
:class-doc-from: class
:show-inheritance:
:members:
:inherited-members:

.. autoclass:: can.bus.BusState
:members:
:undoc-members:


Transmitting
''''''''''''

Writing individual messages to the bus is done by calling the :meth:`~can.BusABC.send` method
and passing a :class:`~can.Message` instance. Periodic sending is controlled by the
:ref:`broadcast manager <bcm>`.
and passing a :class:`~can.Message` instance.

.. code-block:: python
:emphasize-lines: 8
with can.Bus() as bus:
msg = can.Message(
arbitration_id=0xC0FFEE,
data=[0, 25, 0, 1, 3, 1, 4, 1],
is_extended_id=True
)
try:
bus.send(msg)
print(f"Message sent on {bus.channel_info}")
except can.CanError:
print("Message NOT sent")
Periodic sending is controlled by the :ref:`broadcast manager <bcm>`.

Receiving
'''''''''

Reading from the bus is achieved by either calling the :meth:`~can.BusABC.recv` method or
by directly iterating over the bus::

for msg in bus:
print(msg.data)
with can.Bus() as bus:
for msg in bus:
print(msg.data)

Alternatively the :class:`~can.Listener` api can be used, which is a list of :class:`~can.Listener`
subclasses that receive notifications when new messages arrive.
Alternatively the :ref:`listeners_doc` api can be used, which is a list of various
:class:`~can.Listener` implementations that receive and handle messages from a :class:`~can.Notifier`.


Filtering
Expand All @@ -67,6 +74,20 @@ Example defining two filters, one to pass 11-bit ID ``0x451``, the other to pass
See :meth:`~can.BusABC.set_filters` for the implementation.

Bus API
'''''''

.. autoclass:: can.Bus
:class-doc-from: class
:show-inheritance:
:members:
:inherited-members:

.. autoclass:: can.bus.BusState
:members:
:undoc-members:


Thread safe bus
'''''''''''''''

Expand Down
8 changes: 8 additions & 0 deletions doc/errors.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
.. _errors:

Error Handling
==============

.. automodule:: can.exceptions
:members:
:show-inheritance:
4 changes: 2 additions & 2 deletions doc/history.rst
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
History and Roadmap
===================
History
=======

Background
----------
Expand Down
16 changes: 9 additions & 7 deletions doc/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -8,22 +8,22 @@ different hardware devices, and a suite of utilities for sending and receiving
messages on a CAN bus.

**python-can** runs any where Python runs; from high powered computers
with commercial `CAN to usb` devices right down to low powered devices running
with commercial `CAN to USB` devices right down to low powered devices running
linux such as a BeagleBone or RaspberryPi.

More concretely, some example uses of the library:

- Passively logging what occurs on a CAN bus. For example monitoring a
* Passively logging what occurs on a CAN bus. For example monitoring a
commercial vehicle using its **OBD-II** port.

- Testing of hardware that interacts via CAN. Modules found in
modern cars, motocycles, boats, and even wheelchairs have had components tested
* Testing of hardware that interacts via CAN. Modules found in
modern cars, motorcycles, boats, and even wheelchairs have had components tested
from Python using this library.

- Prototyping new hardware modules or software algorithms in-the-loop. Easily
* Prototyping new hardware modules or software algorithms in-the-loop. Easily
interact with an existing bus.

- Creating virtual modules to prototype CAN bus communication.
* Creating virtual modules to prototype CAN bus communication.


Brief example of the library in action: connecting to a CAN bus, creating and sending a message:
Expand All @@ -37,12 +37,14 @@ Brief example of the library in action: connecting to a CAN bus, creating and se
Contents:

.. toctree::
:maxdepth: 2
:maxdepth: 1

installation
configuration
api
interfaces
virtual-interfaces
plugin-interface
scripts
development
history
Expand Down
21 changes: 15 additions & 6 deletions doc/installation.rst
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,24 @@ Installation
============


Install ``can`` with ``pip``:
::
Install the ``can`` package from PyPi with ``pip`` or similar::

$ pip install python-can


As most likely you will want to interface with some hardware, you may
also have to install platform dependencies. Be sure to check any other
specifics for your hardware in :doc:`interfaces`.


.. warning::
As most likely you will want to interface with some hardware, you may
also have to install platform dependencies. Be sure to check any other
specifics for your hardware in :doc:`interfaces`.

Many interfaces can install their dependencies at the same time as ``python-can``,
for instance the interface ``serial`` includes the ``pyserial`` dependency which can
be installed with the ``serial`` extra::

$ pip install python-can[serial]



GNU/Linux dependencies
Expand Down Expand Up @@ -99,7 +108,7 @@ To install ``python-can`` using the CANtact driver backend:

If ``python-can`` is already installed, the CANtact backend can be installed separately:

``python3 -m pip install cantact``
``pip install cantact``

Additional CANtact documentation is available at `cantact.io <https://cantact.io>`__.

Expand Down
67 changes: 7 additions & 60 deletions doc/interfaces.rst
Original file line number Diff line number Diff line change
@@ -1,14 +1,18 @@
.. _can interface modules:

CAN Interface Modules
---------------------
Hardware Interfaces
===================

**python-can** hides the low-level, device-specific interfaces to controller
area network adapters in interface dependant modules. However as each hardware
device is different, you should carefully go through your interface's
documentation.

The available interfaces are:
.. note::
The *Interface Names* are listed in :doc:`configuration`.


The available hardware interfaces are:

.. toctree::
:maxdepth: 1
Expand All @@ -32,63 +36,6 @@ The available interfaces are:
interfaces/socketcan
interfaces/socketcand
interfaces/systec
interfaces/udp_multicast
interfaces/usb2can
interfaces/vector
interfaces/virtual

The *Interface Names* are listed in :doc:`configuration`.


.. _plugin interface:

Plugin Interface
^^^^^^^^^^^^^^^^

External packages can register new interfaces by using the ``can.interface`` entry point
in its project configuration. The format of the entry point depends on your project
configuration format (*pyproject.toml*, *setup.cfg* or *setup.py*).

In the following example ``module`` defines the location of your bus class inside your
package e.g. ``my_package.subpackage.bus_module`` and ``classname`` is the name of
your :class:`can.BusABC` subclass.

.. tab:: pyproject.toml (PEP 621)

.. code-block:: toml
# Note the quotes around can.interface in order to escape the dot .
[project.entry-points."can.interface"]
interface_name = "module:classname"
.. tab:: setup.cfg

.. code-block:: ini
[options.entry_points]
can.interface =
interface_name = module:classname
.. tab:: setup.py

.. code-block:: python
from setuptools import setup
setup(
# ...,
entry_points = {
'can.interface': [
'interface_name = module:classname'
]
}
)
The ``interface_name`` can be used to
create an instance of the bus in the **python-can** API:

.. code-block:: python
import can

bus = can.Bus(interface="interface_name", channel=0)
Loading

0 comments on commit 2e2f157

Please sign in to comment.