<commit_before>'''
Module contains top-level generators.
'''
import hashlib
import json
import logging
import os

from builtins import zip

from netort.resource import manager as resource

from . import format as fmt
from . import info
from .config import ComponentFactory


class AmmoFactory(object):
    '''
    A generator that produces ammo.
    '''

    def __init__(self, factory):
        '''
        Factory parameter is a configured ComponentFactory that
        is able to produce load plan and ammo generator.
        '''
        self.factory = factory
        self.load_plan = factory.get_load_plan()
        self.ammo_generator = factory.get_ammo_generator()
        self.filter = factory.get_filter()
        self.marker = factory.get_marker()

    def __iter__(self):
        '''
        Returns a generator of (timestamp, marker, missile) tuples
        where missile is in a string representation. Load Plan (timestamps
        generator) and ammo generator are taken from the previously
        configured ComponentFactory, passed as a parameter to the
        __init__ method of this class.
        '''
        ammo_stream = (
            ammo
            for ammo in ((missile, marker or self.marker(missile))
                         for missile, marker in self.ammo_generator)
            if self.filter(ammo))

        return ((timestamp, marker or self.marker(missile), missile)
                for timestamp, (missile, marker
                                ) in zip(self.load_plan, ammo_stream))


class Stepper(object):
    def __init__(self, core, **kwargs):
        info.status = info.StepperStatus()
        info.status.core = core
        self.af = AmmoFactory(ComponentFactory(**kwargs))
        self.ammo = fmt.Stpd(self.af)

    def write(self, f):
        for missile in self.ammo:
            f.write(missile)
            try:
                info.status.inc_ammo_count()
            except StopIteration:
                break


class LoadProfile(object):

    def __init__(self, load_type, schedule):
        self.load_type = load_type
        self.schedule = self.__make_steps(schedule)

    def is_rps(self):
        return self.load_type == 'rps'

    def is_instances(self):
        return self.load_type == 'instances'

    @staticmethod
    def __make_steps(schedule):
        steps = []
        for step in " ".join(schedule.split("\n")).split(')'):
            if step.strip():
                steps.append(step.strip() + ')')
        return steps


class StepperWrapper(object):
    # TODO: review and rewrite this class
    '''
    Wrapper for cached stepper functionality
    '''
    OPTION_LOAD = 'load_profile'
    OPTION_LOAD_TYPE = 'load_type'
    OPTION_SCHEDULE = 'schedule'
    OPTION_STEPS = 'steps'
    OPTION_TEST_DURATION = 'test_duration'
    OPTION_AMMO_COUNT = 'ammo_count'
    OPTION_LOOP = 'loop'
    OPTION_LOOP_COUNT = 'loop_count'
    OPTION_AMMOFILE = "ammofile"
    OPTION_LOADSCHEME = 'loadscheme'
    OPTION_INSTANCES_LIMIT = 'instances'

    def __init__(self, core, cfg):
        self.log = logging.getLogger(__name__)
        self.core = core
        self.cfg = cfg

        self.cache_dir = '.'

        # per-shoot params
        self.instances = 1000
        self.http_ver = '1.0'
        self.ammo_file = None
        self.loop_limit = -1
        self.ammo_limit = -1
        self.uris = []
        self.headers = []
        self.autocases = 0
        self.enum_ammo = False
        self.use_caching = True
        self.force_stepping = None
        self.chosen_cases = []

        # out params
        self.stpd = None
        self.steps = []
        self.ammo_count = 1
        self.duration = 0
        self.loop_count = 0
        self.loadscheme = ""
        self.file_cache = 8192

    def get_option(self, option, param2=None):
        ''' get_option wrapper'''
        result = self.cfg[option]
        self.log.debug(
            "Option %s = %s", option, result)
        return result

    @staticmethod
    def get_available_options():
        opts = [
            StepperWrapper.OPTION_AMMOFILE, StepperWrapper.OPTION_LOOP,
            StepperWrapper.OPTION_SCHEDULE, StepperWrapper.OPTION_INSTANCES_LIMIT
        ]
        opts += [
            "instances_schedule", "uris", "headers", "header_http", "autocases",
            "enum_ammo", "ammo_type", "ammo_limit"
        ]
        opts += [
            "use_caching", "cache_dir", "force_stepping", "file_cache",
            "chosen_cases"
        ]
        return opts

    def read_config(self):
        ''' stepper part of reading options '''
        self.log.info("Configuring StepperWrapper...")
        self.ammo_file = self.get_option(self.OPTION_AMMOFILE)
        self.ammo_type = self.get_option('ammo_type')
        if self.ammo_file:
            self.ammo_file = os.path.expanduser(self.ammo_file)
        self.loop_limit = self.get_option(self.OPTION_LOOP)
        self.ammo_limit = self.get_option("ammo_limit")

        self.load_profile = LoadProfile(**self.get_option('load_profile'))

        self.instances = int(<commit_msg>adding support for relative file path for ammo file<commit_after>'''
Module contains top-level generators.
'''
import hashlib
import json
import logging
import os

from builtins import zip

from netort.resource import manager as resource

from . import format as fmt
from . import info
from .config import ComponentFactory


class AmmoFactory(object):
    '''
    A generator that produces ammo.
    '''

    def __init__(self, factory):
        '''
        Factory parameter is a configured ComponentFactory that
        is able to produce load plan and ammo generator.
        '''
        self.factory = factory
        self.load_plan = factory.get_load_plan()
        self.ammo_generator = factory.get_ammo_generator()
        self.filter = factory.get_filter()
        self.marker = factory.get_marker()

    def __iter__(self):
        '''
        Returns a generator of (timestamp, marker, missile) tuples
        where missile is in a string representation. Load Plan (timestamps
        generator) and ammo generator are taken from the previously
        configured ComponentFactory, passed as a parameter to the
        __init__ method of this class.
        '''
        ammo_stream = (
            ammo
            for ammo in ((missile, marker or self.marker(missile))
                         for missile, marker in self.ammo_generator)
            if self.filter(ammo))

        return ((timestamp, marker or self.marker(missile), missile)
                for timestamp, (missile, marker
                                ) in zip(self.load_plan, ammo_stream))


class Stepper(object):
    def __init__(self, core, **kwargs):
        info.status = info.StepperStatus()
        info.status.core = core
        self.af = AmmoFactory(ComponentFactory(**kwargs))
        self.ammo = fmt.Stpd(self.af)

    def write(self, f):
        for missile in self.ammo:
            f.write(missile)
            try:
                info.status.inc_ammo_count()
            except StopIteration:
                break


class LoadProfile(object):

    def __init__(self, load_type, schedule):
        self.load_type = load_type
        self.schedule = self.__make_steps(schedule)

    def is_rps(self):
        return self.load_type == 'rps'

    def is_instances(self):
        return self.load_type == 'instances'

    @staticmethod
    def __make_steps(schedule):
        steps = []
        for step in " ".join(schedule.split("\n")).split(')'):
            if step.strip():
                steps.append(step.strip() + ')')
        return steps


class StepperWrapper(object):
    # TODO: review and rewrite this class
    '''
    Wrapper for cached stepper functionality
    '''
    OPTION_LOAD = 'load_profile'
    OPTION_LOAD_TYPE = 'load_type'
    OPTION_SCHEDULE = 'schedule'
    OPTION_STEPS = 'steps'
    OPTION_TEST_DURATION = 'test_duration'
    OPTION_AMMO_COUNT = 'ammo_count'
    OPTION_LOOP = 'loop'
    OPTION_LOOP_COUNT = 'loop_count'
    OPTION_AMMOFILE = "ammofile"
    OPTION_LOADSCHEME = 'loadscheme'
    OPTION_INSTANCES_LIMIT = 'instances'

    def __init__(self, core, cfg):
        self.log = logging.getLogger(__name__)
        self.core = core
        self.cfg = cfg

        self.cache_dir = '.'

        # per-shoot params
        self.instances = 1000
        self.http_ver = '1.0'
        self.ammo_file = None
        self.loop_limit = -1
        self.ammo_limit = -1
        self.uris = []
        self.headers = []
        self.autocases = 0
        self.enum_ammo = False
        self.use_caching = True
        self.force_stepping = None
        self.chosen_cases = []

        # out params
        self.stpd = None
        self.steps = []
        self.ammo_count = 1
        self.duration = 0
        self.loop_count = 0
        self.loadscheme = ""
        self.file_cache = 8192

    def get_option(self, option, param2=None):
        ''' get_option wrapper'''
        result = self.cfg[option]
        self.log.debug(
            "Option %s = %s", option, result)
        return result

    @staticmethod
    def get_available_options():
        opts = [
            StepperWrapper.OPTION_AMMOFILE, StepperWrapper.OPTION_LOOP,
            StepperWrapper.OPTION_SCHEDULE, StepperWrapper.OPTION_INSTANCES_LIMIT
        ]
        opts += [
            "instances_schedule", "uris", "headers", "header_http", "autocases",
            "enum_ammo", "ammo_type", "ammo_limit"
        ]
        opts += [
            "use_caching", "cache_dir", "force_stepping", "file_cache",
            "chosen_cases"
        ]
        return opts

    def read_config(self):
        ''' stepper part of reading options '''
        self.log.info("Configuring StepperWrapper...")
        self.ammo_file = self.get_option(self.OPTION_AMMOFILE)
        self.ammo_type = self.get_option('ammo_type')
        if self.ammo_file:
            self.ammo_file = os.path.abspath(os.path.expanduser(self.ammo_file))
        self.loop_limit = self.get_option(self.OPTION_LOOP)
        self.ammo_limit = self.get_option("ammo_limit")

        self.load_profile = LoadProfile(**self.get_option('load_profile'))

        self.instances = int(
{'fraction_non_alphanumeric': 0.0977803852547179, 'fraction_numerical': 0.0033245330986604086, 'mean_word_length': 2.165583410708759, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 2, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5972282', 'n_tokens_mistral': 3094, 'n_tokens_neox': 3014, 'n_words': 709}