Yes, this is possible and quite common for packages that serve as both command-line tools and imported libraries.
In setup.py, add a module's function as an entry point:
setuptools.setup(
...
entry_points={'console_scripts': [
'foo = my_package.some_module:main_func',
]},
...
)
To create a script named foo that calls the my_func function inside of my_package.some_module. Read more at https://pythonhosted.org/setuptools/setuptools.html#automatic-script-creation.
It is also a convention it to add:
#!/usr/bin/env python
...
if __name__ == '__main__':
my_func()
to the modules that can be called as "scripts" where my_func is the function you'd like to call externally.
Here is an example of setup.py:
https://github.com/jacebrowning/gdm/blob/fa998167f5f6de64bc8bdfd8b9433870d79ef814/setup.py#L28-L31
and a callable module: