Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We鈥檒l occasionally send you account related emails.

Already on GitHub? Sign in to your account

nn.Module.forward has no docstring #43057

Closed
olliethomas opened this issue Aug 14, 2020 · 3 comments
Closed

nn.Module.forward has no docstring #43057

olliethomas opened this issue Aug 14, 2020 · 3 comments
Labels
module: nn Related to torch.nn triaged This issue has been looked at a team member, and triaged and prioritized into an appropriate module

Comments

@olliethomas
Copy link
Contributor

olliethomas commented Aug 14, 2020

馃悰 Bug

from 1.5.1 to 1.6, the definition of nn.Module.forward changed and no longer contains a docstring.

forward in 1.5.1

class Module(object):
        def forward(self, *input):
        r"""Defines the computation performed at every call.
        Should be overridden by all subclasses.
        .. note::
            Although the recipe for forward pass needs to be defined within
            this function, one should call the :class:`Module` instance afterwards
            instead of this since the former takes care of running the
            registered hooks while the latter silently ignores them.
        """
        raise NotImplementedError

forward in 1.6

class Module:
    def _forward_unimplemented(self, *input: Any) -> None:
        raise NotImplementedError

    r"""Defines the computation performed at every call.

    Should be overridden by all subclasses.

    .. note::
        Although the recipe for forward pass needs to be defined within
        this function, one should call the :class:`Module` instance afterwards
        instead of this since the former takes care of running the
        registered hooks while the latter silently ignores them.
    """
    forward: Callable[..., Any] = _forward_unimplemented

In our code base, instead of adding docstrings to functions that implement methods of a superclass, we have an @implements decorator that uses the docstring of the superclass.

for reference

class implements:  # pylint: disable=invalid-name
    """Mark a function as implementing an interface."""

    def __init__(self, interface: Type):
        """Instantiate the decorator.

        Args:
            interface: the interface that is implemented
        """
        self.interface = interface

    def __call__(self, func: _F) -> _F:
        """Take a function and return it unchanged."""
        super_method = getattr(self.interface, func.__name__, None)
        assert super_method is not None, f"'{func.__name__}' does not exist in {self.interface}"
        assert super_method.__doc__, f"'{super_method}' has no docstring"
        return func

When we update from torch==1.5.1 to torch==1.6.0, the assertion assert super_method.__doc__ fails.

To Reproduce

Steps to reproduce the behavior:

in 1.5.1 the following can be successfully executed

import torch
from torch import nn
assert getattr(nn.Module, nn.Module.forward.__name__, None).__doc__

in 1.6.0 the same statement raises an AssertionError

import torch
from torch import nn
assert getattr(nn.Module, nn.Module.forward.__name__, None).__doc__
> AssertionError

Expected behavior

In the reproduction steps, an error should not be raised. Ideally, forward would have a docstring

Environment

  • PyTorch Version (e.g., 1.0): 1.6.0
  • OS (e.g., Linux): Mac OSX 10.15.6 (x86_64)
  • How you installed PyTorch (conda, pip, source): pip
  • Build command you used (if compiling from source):
  • Python version: 3.7.3
  • CUDA/cuDNN version: No CUDA
  • GPU models and configuration: No CUDA
  • Any other relevant information: None

Additional context

As an example of a solution, if the single line comments above the definition for _forward_unimplemented are moved to be the docstring for that function, the AssertionError in the Reproduce steps is no longer raised.

Current - raises AssertionError with assert getattr(nn.Module, nn.Module.forward.__name__, None).__doc__

# Trick mypy into not applying contravariance rules to inputs by defining
# forward as a value, rather than a function.  See also
# https://github.com/python/mypy/issues/8795
def _forward_unimplemented(self, *input: Any) -> None:
    raise NotImplementedError

Example solution - AssertionError no longer raised.

def _forward_unimplemented(self, *input: Any) -> None:
    '''Trick mypy into not applying contravariance rules to inputs by defining
    forward as a value, rather than a function.  See also
    https://github.com/python/mypy/issues/8795
    '''
    raise NotImplementedError

cc @albanD @mruberry

olliethomas added a commit to olliethomas/pytorch that referenced this issue Aug 14, 2020
A small change that adds a docstring that can be found with `getattr(nn.Module, nn.Module.forward.__name__, None).__doc__`

Closes pytorch#43057
@izdeby izdeby added module: nn Related to torch.nn triaged This issue has been looked at a team member, and triaged and prioritized into an appropriate module labels Aug 14, 2020
@mruberry
Copy link
Collaborator

We would accept a PR fixing this. I left a comment on the linked PR.

@albanD
Copy link
Collaborator

albanD commented Aug 14, 2020

cc @ezyang I think this was introduced by this PR: #38211
Is there potentially more issues like that from that PR?

@ezyang
Copy link
Contributor

ezyang commented Aug 18, 2020

@albanD No, Module.forward was the only method that got this treatment in the typing module.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
module: nn Related to torch.nn triaged This issue has been looked at a team member, and triaged and prioritized into an appropriate module
Projects
None yet
Development

Successfully merging a pull request may close this issue.

5 participants