Esempio n. 1
0
def create_community_user(session: orm.Session,
                          app: Optional[sanic.Sanic] = None) -> None:
    from rasax.community.services.role_service import RoleService
    from rasax.community.services.settings_service import SettingsService

    role_service = RoleService(session)
    role_service.init_roles(project_id=constants.COMMUNITY_PROJECT_NAME)

    settings_service = SettingsService(session)
    password = settings_service.get_community_user_password()
    is_password_generated = False

    # only re-assign password in local mode or if it doesn't exist
    if config.LOCAL_MODE or not password:
        password = os.environ.get(constants.ENV_RASA_X_PASSWORD)
        if not password:
            password = random_password()
            is_password_generated = True
        settings_service.save_community_user_password(password)

    user_service = UserService(session)
    user_service.insert_or_update_user(constants.COMMUNITY_USERNAME, password,
                                       constants.COMMUNITY_TEAM_NAME)

    if app:
        run_operation_in_single_sanic_worker(
            app, AppStartedCallable(password, is_password_generated))
Esempio n. 2
0
    async def get_model_config(request, project_id, user=None):
        settings_service = SettingsService(request[REQUEST_DB_SESSION_KEY])
        stack_config = settings_service.get_config(user["team"], project_id)
        if not stack_config:
            return rasa_x_utils.error(http.HTTPStatus.NOT_FOUND,
                                      "SettingsFailed",
                                      "Could not find settings.")

        yaml_config = rasa_x_utils.dump_yaml(stack_config)

        return response.text(yaml_config)
def _create_initial_project(session) -> None:
    if not session.query(Project).first():
        settings_service = SettingsService(session)
        settings_service.init_project(
            rasa_x_config.team_name, rasa_x_config.project_name
        )

        session.commit()
        logger.debug(
            f"No projects present. Created initial default project '{rasa_x_config.project_name}'."
        )
def _stack_service(request: Request,
                   default_environment: Text) -> StackService:
    settings_service = SettingsService(request[REQUEST_DB_SESSION_KEY])

    environment = rasa_x_utils.deployment_environment_from_request(
        request, default_environment)
    service = settings_service.get_stack_service(environment)
    if not service:
        raise ValueError(
            f"Service for requested environment '{environment}' not found")

    return service
Esempio n. 5
0
 async def save_model_config(request, project_id, user=None):
     settings_service = SettingsService(request[REQUEST_DB_SESSION_KEY])
     try:
         config_yaml = settings_service.inspect_and_save_yaml_config_from_request(
             request.body, user["team"], project_id)
         return response.text(config_yaml)
     except YAMLError as e:
         return rasa_x_utils.error(
             400, "InvalidConfig",
             f"Failed to read configuration file.  Error: {e}")
     except InvalidConfigError as e:
         return rasa_x_utils.error(http.HTTPStatus.UNPROCESSABLE_ENTITY,
                                   "ConfigMissingKeys", f"Error: {e}")
    async def create_project(request: Request, project_id: Text,
                             user: Dict) -> HTTPResponse:
        settings_service = SettingsService(request[REQUEST_DB_SESSION_KEY])

        try:
            project = settings_service.init_project(user["team"], project_id)
        except ProjectException as e:
            return rasa_x_utils.error(404, "ProjectCreationError", details=e)

        user_service = UserService(request[REQUEST_DB_SESSION_KEY])
        user_service.assign_project_to_user(user, project_id)

        return response.json(project)
Esempio n. 7
0
    def _update_community_user_password(self, username: Text,
                                        password: Text) -> None:
        if username == COMMUNITY_USERNAME:
            from rasax.community.services.settings_service import SettingsService

            SettingsService(
                self.session).save_community_user_password(password)
Esempio n. 8
0
def initialise_services(_session):
    return (
        UserService(_session),
        SettingsService(_session),
        DomainService(_session),
        RoleService(_session),
    )
    async def get_environment_config(request: Request) -> HTTPResponse:
        settings_service = SettingsService(request[REQUEST_DB_SESSION_KEY])
        environments = settings_service.get_environments_config(
            config.project_name)

        if not environments:
            return rasa_x_utils.error(
                400,
                "EnvironmentSettingsNotFound",
                "could not find environment settings",
            )

        return response.json({
            "environments":
            utils.dump_yaml(environments.get("environments"))
        })
    async def minimum_compatible_version(self) -> Optional[Text]:
        from rasax.community.services.settings_service import SettingsService

        if config.LOCAL_MODE:
            # In local mode Rasa X and Rasa are in the same environment
            from rasa.constants import MINIMUM_COMPATIBLE_VERSION

            return MINIMUM_COMPATIBLE_VERSION

        settings_service = SettingsService(self.session)
        stack_service = settings_service.get_stack_service(self.environment)
        info = await stack_service.version()
        if info:
            return info.get("minimum_compatible_version")
        else:
            logger.debug("Couldn't get a minimum compatible model version.")
            return None
Esempio n. 11
0
def _initialize_with_local_data(
    project_path: Text,
    data_path: Text,
    session: Session,
    rasa_port: Union[int, Text],
    config_path: Text,
) -> Tuple[Dict[Text, Any], List[Dict[Text, Any]], TrainingData]:

    settings_service = SettingsService(session)
    default_env = default_environments_config_local(rasa_port)
    settings_service.save_environments_config(COMMUNITY_PROJECT_NAME,
                                              default_env.get("environments"))

    loop = asyncio.get_event_loop()
    # inject data
    domain, story_blocks, nlu_data = loop.run_until_complete(
        rasax.community.initialise.inject_files_from_disk(
            project_path, data_path, session, config_path=config_path))

    # dump domain once
    domain_service = DomainService(session)
    domain_service.dump_domain()
    return domain, story_blocks, nlu_data
Esempio n. 12
0
async def inject_files_from_disk(
    project_path: Union[Path, Text],
    data_path: Text,
    session: orm.Session,
    username: Optional[Text] = constants.COMMUNITY_USERNAME,
    config_path: Optional[Text] = config.default_config_path,
) -> Tuple[Dict[Text, Any], List[Dict[Text, Any]], "NluTrainingData"]:
    """Injects local files into database.

    Args:
        project_path: Path to the project of which the data should be injected.
        data_path: Path to the data within this project.
        session: Database session.
        username: The username which is used to inject the data.
        config_path: Path to the config file within the project

    Returns:
        Tuple of domain, stories, and NLU training data.
    """
    import rasa.data
    from rasax.community.local import LOCAL_DOMAIN_PATH
    from rasax.community.services.data_service import DataService
    from rasax.community.services.settings_service import SettingsService

    utils.set_project_directory(project_path)

    domain_service = DomainService(session)
    domain = inject_domain(
        os.path.join(project_path, LOCAL_DOMAIN_PATH),
        domain_service,
        constants.COMMUNITY_PROJECT_NAME,
        username,
    )

    settings_service = SettingsService(session)
    inject_config(os.path.join(project_path, config_path), settings_service)

    story_files, nlu_files = rasa.data.get_core_nlu_files([data_path])

    story_service = StoryService(session)
    story_blocks = await inject_stories(story_files, story_service, username,
                                        constants.COMMUNITY_TEAM_NAME)

    data_service = DataService(session)
    nlu_data = inject_nlu_data(nlu_files, constants.COMMUNITY_PROJECT_NAME,
                               username, data_service)

    return domain, story_blocks, nlu_data
Esempio n. 13
0
    async def train_model(request, project_id):
        stack_services = SettingsService(
            request[REQUEST_DB_SESSION_KEY]).stack_services(project_id)
        environment = utils.deployment_environment_from_request(
            request, "worker")
        stack_service = stack_services[environment]

        try:
            training_start = time.time()
            content = await stack_service.start_training_process()

            telemetry.track(telemetry.MODEL_TRAINED_EVENT)

            model_name = await _model_service(request).save_trained_model(
                project_id, content)

            nlg_service = NlgService(request[REQUEST_DB_SESSION_KEY])
            nlg_service.mark_responses_as_used(training_start)

            return response.json({
                "info": "New model trained.",
                "model": model_name
            })
        except FileExistsError as e:
            logger.error(e)
            return response.json(
                {
                    "info": "Model already exists.",
                    "path": str(e)
                },
                http.HTTPStatus.CREATED,
            )
        except ValueError as e:
            logger.error(e)
            return rasa_x_utils.error(
                http.HTTPStatus.BAD_REQUEST,
                "StackTrainingFailed",
                "Unable to train on data containing retrieval intents.",
                details=e,
            )
        except ClientError as e:
            logger.error(e)
            return rasa_x_utils.error(
                http.HTTPStatus.INTERNAL_SERVER_ERROR,
                "StackTrainingFailed",
                "Failed to train a Rasa model.",
                details=e,
            )
async def _get_project_status_event(
        session: Session,
        project_id: Text = config.project_name) -> Dict[Text, Any]:
    """Collect data used in `status` event.

    Args:
        session: Database session.
        project_id: The project ID.

    Returns:
        A dictionary containing statistics describing the current project's status.
    """

    from rasax.community.services.event_service import EventService
    from rasax.community.services.domain_service import DomainService
    from rasax.community.services.model_service import ModelService
    from rasax.community.services.data_service import DataService
    from rasax.community.services.story_service import StoryService
    from rasax.community.services.settings_service import SettingsService
    import rasax.community.services.test_service as test_service
    from rasax.community.services import stack_service

    event_service = EventService(session)
    domain_service = DomainService(session)
    model_service = ModelService(config.rasa_model_dir, session)
    data_service = DataService(session)
    story_service = StoryService(session)
    settings_service = SettingsService(session)

    domain = domain_service.get_domain(project_id) or {}
    nlu_data = data_service.get_nlu_training_data_object(project_id=project_id)
    stories = story_service.fetch_stories()

    num_conversations = event_service.get_conversation_metadata_for_all_clients(
    ).count
    num_events = event_service.get_events_count()
    num_models = model_service.get_model_count()
    lookup_tables = data_service.get_lookup_tables(project_id,
                                                   include_filenames=True)
    num_lookup_table_files = len(
        {table["filename"]
         for table in lookup_tables})
    num_lookup_table_entries = sum(
        table.get("number_of_elements", 0) for table in lookup_tables)
    synonyms = data_service.get_entity_synonyms(project_id)
    num_synonyms = sum(len(entry["synonyms"]) for entry in synonyms)
    num_regexes = data_service.get_regex_features(project_id).count

    rasa_services = settings_service.stack_services(project_id)
    version_responses = await stack_service.collect_version_calls(
        rasa_services, timeout_in_seconds=ENVIRONMENT_LIVE_TIMEOUT)

    environment_names = _environment_names(rasa_services)

    tags = event_service.get_all_conversation_tags()
    conversations_with_tags = set()
    for tag in tags:
        conversations_with_tags.update(tag["conversations"])

    e2e_tests = test_service.get_tests_from_file()

    return {
        # Use the SHA256 of the project ID in case its value contains
        # information about the user's use of Rasa X. On the analytics side,
        # having the original value or the hash makes no difference. This
        # reasoning is also applied on other values sent in this module.
        "project":
        hashlib.sha256(project_id.encode("utf-8")).hexdigest(),
        "local_mode":
        config.LOCAL_MODE,
        "rasa_x":
        __version__,
        "rasa_open_source":
        _rasa_version(version_responses),
        "num_intent_examples":
        len(nlu_data.intent_examples),
        "num_entity_examples":
        len(nlu_data.entity_examples),
        "num_actions":
        len(domain.get("actions", [])),
        "num_templates":
        len(
            domain.get("responses", [])
        ),  # Old nomenclature from when 'responses' were still called 'templates' in the domain
        "num_slots":
        len(domain.get("slots", [])),
        "num_forms":
        len(domain.get("forms", [])),
        "num_intents":
        len(domain.get("intents", [])),
        "num_entities":
        len(domain.get("entities", [])),
        "num_stories":
        len(stories),
        "num_conversations":
        num_conversations,
        "num_events":
        num_events,
        "num_models":
        num_models,
        "num_lookup_table_files":
        num_lookup_table_files,
        "num_lookup_table_entries":
        num_lookup_table_entries,
        "num_synonyms":
        num_synonyms,
        "num_regexes":
        num_regexes,
        "num_environments":
        len(environment_names),
        "environment_names":
        environment_names,
        "num_live_environments":
        _number_of_live_rasa_environments(version_responses),
        "uptime_seconds":
        utils.get_uptime(),
        "num_tags":
        len(tags),
        "num_conversations_with_tags":
        len(conversations_with_tags),
        "num_e2e_tests":
        len(e2e_tests),
    }
    def _dump_config(self, configuration_change: Dict[Text, Text]) -> None:
        from rasax.community.services.settings_service import SettingsService

        settings_service = SettingsService(self.session)
        settings_service.dump_config(configuration_change["team"],
                                     configuration_change["project_id"])
def _rasa_services(request: Request) -> Dict[Text, StackService]:
    settings_service = SettingsService(request[REQUEST_DB_SESSION_KEY])
    return settings_service.stack_services()