def _check_user(self, username, pw_hash): username = str(username) pw_hash = str(pw_hash) # This function is really just a post-validation item. default_store = api.get_default_store() current_branch = api.get_current_branch(default_store) user = LoginUser.authenticate(default_store, username, pw_hash, current_branch) # Dont know why, but some users have this empty. Prevent user from # login in, since it will break later if not user.profile: msg = (_("User '%s' has no profile set, " "but this should not happen.") % user.username + '\n\n' + _("Please contact your system administrator or Stoq team.")) warning(msg) raise LoginError(_("User does not have a profile")) user.login(api.get_current_station(default_store)) # ICurrentUser might already be provided which is the case when # creating a new database, thus we need to replace it. provide_utility(ICurrentUser, user, replace=True) return user
def _provide_current_station(station_name=None, branch_name=None): if not station_name: station_name = get_hostname() store = new_store() if branch_name: branch = store.find( Person, And(Person.name == branch_name, Branch.person_id == Person.id)).one() else: branches = store.find(Branch) if branches.count() == 0: person = Person(name=u"test", store=store) Company(person=person, store=store) branch = Branch(person=person, store=store) else: branch = branches[0] provide_utility(ICurrentBranch, branch) station = BranchStation.get_station(store, branch, station_name) if not station: station = BranchStation.create(store, branch, station_name) assert station assert station.is_active provide_utility(ICurrentBranchStation, station) store.commit(close=True)
def _setup_domain_slave_mapper(self): from stoqlib.lib.component import provide_utility from stoq.lib.gui.interfaces import IDomainSlaveMapper from stoq.lib.gui.slaves.domainslavemapper import DefaultDomainSlaveMapper provide_utility(IDomainSlaveMapper, DefaultDomainSlaveMapper(), replace=True)
def wrapper(*args, **kwargs): # token should be sent through a header using the format 'Bearer <token>' auth = request.headers.get('Authorization', '').split('Bearer ') if len(auth) != 2: log.warning('Invalid Authorization header: %s', request.headers.get('Authorization')) abort(401) with api.new_store() as store: access_token = AccessToken.get_by_token(store=store, token=auth[1]) if not access_token: log.warning('Token not found: %s', auth) abort(403, "invalid token {}".format(auth[1])) if not access_token.is_valid(): abort(403, "token {}".format(access_token.status)) # FIXME: the user utility acts as a singleton and since we'd like to have stoqserver API # accepting requests from different stations (users), we cannot use this pattern as it # can lead to racing problems. For now we are willing to put a lock in every request, # but the final solution should be a refactor that makes every endpoint use the user # provided in the token payload instead of this 'global' one. user = store.get(LoginUser, access_token.payload['user_id']) provide_utility(ICurrentUser, user, replace=True) return f(*args, **kwargs)
def _setup_ui_dialogs(self): # This needs to be here otherwise we can't install the dialog if 'STOQ_TEST_MODE' in os.environ: return log.debug('providing graphical notification dialogs') from stoq.lib.gui.base.dialogs import DialogSystemNotifier from stoqlib.lib.interfaces import ISystemNotifier from stoqlib.lib.component import provide_utility provide_utility(ISystemNotifier, DialogSystemNotifier(), replace=True) from gi.repository import Gtk from kiwi.environ import environ from stoq.lib.gui.stockicons import STOQ_LAUNCHER Gtk.Window.set_default_icon_name(STOQ_LAUNCHER) if platform.system() == 'Darwin': from AppKit import NSApplication, NSData, NSImage # FIXME: This should be a 48x48 icon data = environ.get_resource_string('stoq', 'pixmaps', 'hicolor', '24x24', 'actions', 'stoq-launcher.png') data = NSData.alloc().initWithBytes_length_(data, len(data)) icon = NSImage.alloc().initWithData_(data) app = NSApplication.sharedApplication() app.setApplicationIconImage_(icon)
def _provide_app_info(): from stoqlib.lib.interfaces import IAppInfo from stoqlib.lib.appinfo import AppInfo info = AppInfo() info.set(u"name", u"Stoqlib") info.set(u"version", u"1.0.0") provide_utility(IAppInfo, info)
def get_permission_manager(cls): """Returns the payment operation manager""" pm = get_utility(IPermissionManager, None) if not pm: pm = PermissionManager() provide_utility(IPermissionManager, pm) return pm
def test_already_implmeneted_error(): with pytest.raises(NotImplementedError): get_utility(IBanana) provide_utility(IBanana, o) with pytest.raises(AlreadyImplementedError): provide_utility(IBanana, o)
def test_provide_utility(): with pytest.raises(NotImplementedError): get_utility(IBanana) provide_utility(IBanana, o) with pytest.raises(TypeError): provide_utility(object, o)
def test_get_utility(): assert get_utility(IBanana, None) is None provide_utility(IBanana, o) with pytest.raises(TypeError): get_utility(object) assert get_utility(IBanana, o)
def _setup_cookiefile(self): log.debug('setting up cookie file') from stoqlib.lib.component import provide_utility from stoqlib.lib.cookie import Base64CookieFile from stoqlib.lib.interfaces import ICookieFile from stoqlib.lib.osutils import get_application_dir app_dir = get_application_dir() cookiefile = os.path.join(app_dir, "cookie") provide_utility(ICookieFile, Base64CookieFile(cookiefile))
def get_payment_operation_manager(): """Returns the payment operation manager""" pmm = get_utility(IPaymentOperationManager, None) if not pmm: from stoqlib.lib.payment import PaymentOperationManager pmm = PaymentOperationManager() provide_utility(IPaymentOperationManager, pmm) return pmm
def tearDown(self): provide_utility(IAppInfo, self._iappinfo, replace=True) # Shell.bootstrap calls # ProxyLabel.replace('$CURRENCY', get_localeconv()['currency_symbol']) # and that will break uitests if '$CURRENCY' in ProxyLabel._label_replacements: del ProxyLabel._label_replacements['$CURRENCY'] for mocked in self._mocks: mocked.stop()
def _set_person_utilities(): store = new_store() branch = sysparam.get_object(store, 'MAIN_COMPANY') provide_utility(ICurrentBranch, branch) station = BranchStation(name=u"Stoqlib station", branch=branch, store=store, is_active=True) provide_utility(ICurrentBranchStation, station) store.commit(close=True)
def testZopeInterface(self): try: from zope.interface import Interface except ImportError: return class IApple(Interface): pass self.assertRaises(NotImplementedError, get_utility, IApple) provide_utility(IApple, o) self.assertRaises(AlreadyImplementedError, provide_utility, IApple, o)
def test_remove_utility(): with pytest.raises(TypeError): remove_utility(object) with pytest.raises(NotImplementedError): remove_utility(IBanana) provide_utility(IBanana, o) assert remove_utility(IBanana) == o with pytest.raises(NotImplementedError): remove_utility(IBanana)
def _provide_app_info(self): # FIXME: The webservice need the IAppInfo provided to get the stoq # version. We cannot do that workaround there because we don't want to # import stoq inside stoqlib. Either way, this code to download the # egg will move to the plugin dialog soon. from stoqlib.lib.component import provide_utility from stoqlib.lib.appinfo import AppInfo from stoqlib.lib.interfaces import IAppInfo import stoq info = AppInfo() info.set("version", stoq.version) provide_utility(IAppInfo, info)
def get_plugin_manager(): """Provides and returns the plugin manager @attention: Try to always use this instead of getting the utillity by hand, as that could not have been provided before. :returns: an :class:`PluginManager` instance """ manager = get_utility(IPluginManager, None) if not manager: manager = PluginManager() provide_utility(IPluginManager, manager) return manager
def register_config(config): from stoqlib.lib.component import provide_utility global _config _config = config try: provide_utility(IStoqConfig, config, replace=True) except NoConfigurationError: msg = _(u"Error: Stoq configuration is not avaiable. Check that the " "current user has a configuration file (~/.stoq/stoq.conf).") if os.geteuid() == 0: msg += _('\n\nYou are running stoq using sudo. That is not ' 'recommended.') raise SystemExit(msg)
def test_only_admin_can_add_client_credit(self): client = self.create_client() editor = ClientEditor(self.store, client, role_type=Person.ROLE_INDIVIDUAL) self.check_editor(editor, 'client-editor-admin-user') admin_user = api.get_current_user(self.store) salesperson_user = self.store.find(LoginUser, username=u'elias').one() provide_utility(ICurrentUser, salesperson_user, replace=True) editor = ClientEditor(self.store, client, role_type=Person.ROLE_INDIVIDUAL) self.check_editor(editor, 'client-editor-salesperson-user') provide_utility(ICurrentUser, admin_user, replace=True)
def ensure_admin_user(administrator_password): log.info("Creating administrator user") default_store = get_default_store() user = get_admin_user(default_store) if user is None: store = new_store() person = Person(name=_(u'Administrator'), store=store) # Dependencies to create an user. role = EmployeeRole(name=_(u'System Administrator'), store=store) Individual(person=person, store=store) employee = Employee(person=person, role=role, store=store) EmployeeRoleHistory(store=store, role=role, employee=employee, is_active=True, salary=currency(800)) # This is usefull when testing a initial database. Admin user actually # must have all the facets. SalesPerson(person=person, store=store) profile = store.find(UserProfile, name=_(u'Administrator')).one() # Backwards compatibility. this profile used to be in english # FIXME: Maybe its safe to assume the first profile in the table is # the admin. if not profile: profile = store.find(UserProfile, name=u'Administrator').one() log.info("Attaching a LoginUser (%s)" % (USER_ADMIN_DEFAULT_NAME, )) LoginUser(person=person, username=USER_ADMIN_DEFAULT_NAME, password=administrator_password, profile=profile, store=store) store.commit(close=True) # Fetch the user again, this time from the right connection user = get_admin_user(default_store) assert user user.set_password(administrator_password) # We can't provide the utility until it's actually in the database log.info('providing utility ICurrentUser') provide_utility(ICurrentUser, user)
def create_main_branch(store, name): """Creates a new branch and sets it as the main branch for the system :param store: a store :param name: name of the new branch """ person = Person(name=name, store=store) Company(person=person, store=store) branch = Branch(person=person, store=store) sysparam.set_object(store, 'MAIN_COMPANY', branch) provide_utility(ICurrentBranch, branch) admin = get_admin_user(store) admin.add_access_to(branch) return branch
def test_zope_interface(): try: from zope.interface import Interface except ImportError: return class IApple(Interface): pass with pytest.raises(NotImplementedError): get_utility(IApple) provide_utility(IApple, o) with pytest.raises(AlreadyImplementedError): provide_utility(IApple, o)
def provide_database_settings(dbname=None, address=None, port=None, username=None, password=None, createdb=True): """ Provide database settings. :param dbname: :param address: :param port: :param username: :param password: :param create: Create a new empty database if one is missing """ if not username: username = get_username() if not dbname: dbname = username + u'_test' if not address: address = os.environ.get(u'PGHOST', u'') if not port: port = os.environ.get(u'PGPORT', u'5432') if not password: password = u"" # Remove all old utilities pointing to the previous database. utilities.clean() provide_utility(ISystemNotifier, test_system_notifier, replace=True) _provide_application_descriptions() _provide_domain_slave_mapper() _provide_app_info() db_settings.address = address db_settings.port = port db_settings.dbname = dbname db_settings.username = username db_settings.password = password rv = False if createdb or not db_settings.database_exists(dbname): db_settings.clean_database(dbname, force=True) rv = True return rv
def set_current_branch_station(store, station_name, confirm=True): """Registers the current station and the branch of the station as the current branch for the system :param store: a store :param station_name: name of the station to register """ # This is called from stoq-daemon, which doesn't know about Branch yet from stoqlib.lib.parameters import sysparam from stoqlib.domain.person import Branch Branch # pylint: disable=W0104 if station_name is None: station_name = get_hostname() station_name = str(station_name) from stoqlib.domain.station import BranchStation station = store.find(BranchStation, name=station_name).one() if station is None: station = _register_branch_station(store, station_name, confirm=confirm) if not station.is_active: error( _("The computer <u>%s</u> is not active in Stoq") % station_name, _("To solve this, open the administrator application " "and re-activate this computer.")) provide_utility(ICurrentBranchStation, station, replace=True) main_company = sysparam.get_object(store, 'MAIN_COMPANY') if not station.branch and main_company: with new_store() as commit_store: commit_station = commit_store.fetch(station) commit_station.branch = commit_store.fetch(main_company) # The station may still not be associated with a branch when creating an # empty database if station.branch: provide_utility(ICurrentBranch, station.branch, replace=True) return station
def setup_stoq(register_station=False, name='stoqserver', version=stoqserver.version_str, options=None): info = AppInfo() info.set('name', name) info.set('version', version) info.set('ver', version) provide_utility(IAppInfo, info, replace=True) setup(config=get_config(), options=options, register_station=register_station, check_schema=True, load_plugins=True) # This is needed for api calls that requires the current branch set, # e.g. Sale.confirm main_company = api.sysparam.get_object(api.get_default_store(), 'MAIN_COMPANY') provide_utility(ICurrentBranch, main_company, replace=True)
def _set_app_info(self): from stoqlib.lib.component import provide_utility from stoqlib.lib.appinfo import AppInfo from stoqlib.lib.kiwilibrary import library from stoqlib.lib.interfaces import IAppInfo import stoq # FIXME: use only stoq.stoq_version here and all other callsites of # IAppInfo stoq_version = stoq.version stoq_ver = stoq.stoq_version if hasattr(library, 'get_revision'): rev = library.get_revision() if rev is not None: stoq_version += ' ' + rev stoq_ver += (rev,) info = AppInfo() info.set("name", "Stoq") info.set("version", stoq_version) info.set("ver", stoq_ver) info.set("log", self._log_filename) provide_utility(IAppInfo, info)
def _create_station(self, store): # FIXME: This is fishy, we can probably simplify this significantly by # allowing users to connect to the initial database without # having a branch station nor branch registered. # The whole BranchStation/Branch creation is weird, it should # be done at the same place. logger.info('_create_station') if self.create_examples: branch = api.sysparam.get_object(store, 'MAIN_COMPANY') assert branch provide_utility(ICurrentBranch, branch) else: branch = None station_name = get_hostname() if store.find(BranchStation, branch=branch, name=station_name).one(): return station = BranchStation(store=store, is_active=True, branch=branch, name=station_name) provide_utility(ICurrentBranchStation, station)
return sn.warning(short, description, *args, **kwargs) def error(short, description=None): sn = get_utility(ISystemNotifier) log.info("Error: short='%s' description='%s'" % (short, description)) sn.error(short, description) sys.exit(1) def yesno(text, default=-1, *verbs): sn = get_utility(ISystemNotifier) rv = sn.yesno(text, default, *verbs) log.info("Yes/No: text='%s' verbs='%r' rv='%r'" % (text, verbs, rv)) return rv def marker(msg): if os.environ.get('STOQ_DEBUG'): sys.stderr.write('[%.3f] %s\n' % ( get_uptime(), msg, )) # During normall shell startup this is already set, # so only install the text mode version when we starting up # via stoqdbadmin or other ways. if get_utility(ISystemNotifier, None) is None: provide_utility(ISystemNotifier, DefaultSystemNotifier())
def testAlreadyImplemented(self): self.assertRaises(NotImplementedError, get_utility, IBanana) provide_utility(IBanana, o) self.assertRaises(AlreadyImplementedError, provide_utility, IBanana, o)