-
Notifications
You must be signed in to change notification settings - Fork 3
129 Make cycles, scenarioname NB template variables by default #148
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’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
Changes from all commits
3f8df3a
5958aa0
3c6fcf2
e36c507
1499462
ca79599
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,15 +1,17 @@ | ||
| import logging | ||
| import yaml | ||
|
|
||
| from itertools import chain | ||
|
|
||
| from adelphi.exceptions import KeyspaceSelectionException, TableSelectionException, ExportException | ||
| from adelphi.export import BaseExporter | ||
|
|
||
| MAX_NUMERIC_VAL = 1000 ** 3 | ||
| RAMPUP_SCENARIO = "run driver=cql tags=phase:rampup cycles={} threads=auto" | ||
| MAIN_SCENARIO = "run driver=cql tags=phase:main cycles={} threads=auto" | ||
|
|
||
| TEMPLATEVAR_RAMPUP_CYCLES = "TEMPLATE(rampup-cycles,1000)" | ||
| TEMPLATEVAR_MAIN_CYCLES = "TEMPLATE(main-cycles,1000)" | ||
| TEMPLATEVAR_SCENARIO_NAME = "TEMPLATE(scenarioname,default)" | ||
|
|
||
| CQL_TYPES={} | ||
| CQL_TYPES["text"] = "Mod({}); ToString() -> String" | ||
| CQL_TYPES["ascii"] = "Mod({}); ToString() -> String" | ||
|
|
@@ -89,7 +91,12 @@ def __init__(self, cluster, props): | |
|
|
||
| self.rampup_cycles = props["rampup-cycles"] | ||
| self.main_cycles = props["main-cycles"] | ||
| self.numeric_max = min((self.rampup_cycles + self.main_cycles) * 1000, MAX_NUMERIC_VAL) | ||
| self.scenario_name = props["scenario-name"] | ||
| self.numeric_max = \ | ||
| min((self.rampup_cycles + self.main_cycles) * 1000, MAX_NUMERIC_VAL) \ | ||
| if self.rampup_cycles and self.main_cycles \ | ||
| else MAX_NUMERIC_VAL | ||
|
Collaborator
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This reflects the maximum size we can get for numeric values. If the number of cycles is specified we can use this to constrain the number of values in order to increase the likelihood of hits when we do selects on primary keys. |
||
|
|
||
|
|
||
| # Always disable anonymization when generating nosqlbench configs | ||
| real_props = props.copy() | ||
|
|
@@ -107,8 +114,10 @@ def __init__(self, cluster, props): | |
| self.table = next(iter(self.keyspace.tables.values())) | ||
|
|
||
| log.info("Creating nosqlbench config for {}.{}".format(self.keyspace.name, self.table.name)) | ||
| log.info("Number of cycles for rampup phase = {}".format(self.rampup_cycles)) | ||
| log.info("Number of cycles for main phase = {}".format(self.main_cycles)) | ||
| if self.rampup_cycles: | ||
| log.info("Number of cycles for rampup phase = {}".format(self.rampup_cycles)) | ||
| if self.main_cycles: | ||
| log.info("Number of cycles for main phase = {}".format(self.main_cycles)) | ||
| log.info("Max numeric value = {}".format(self.numeric_max)) | ||
|
|
||
|
|
||
|
|
@@ -125,11 +134,11 @@ def each_keyspace(self, ks_fn): | |
|
|
||
|
|
||
| def __get_rampup_scenario(self): | ||
| return RAMPUP_SCENARIO.format(self.rampup_cycles) | ||
| return RAMPUP_SCENARIO.format(self.rampup_cycles or TEMPLATEVAR_RAMPUP_CYCLES) | ||
|
|
||
|
|
||
| def __get_main_scenario(self): | ||
| return MAIN_SCENARIO.format(self.main_cycles) | ||
| return MAIN_SCENARIO.format(self.main_cycles or TEMPLATEVAR_MAIN_CYCLES) | ||
|
|
||
|
|
||
| def __get_dist(self, typename): | ||
|
|
@@ -172,7 +181,7 @@ def __build_schema(self): | |
| """Really more of a config than a schema, but we'll allow it""" | ||
| root = {} | ||
|
|
||
| root["scenarios"] = {"TEMPLATE(scenarioname,default)":[self.__get_rampup_scenario(), self.__get_main_scenario()]} | ||
| root["scenarios"] = {self.scenario_name or TEMPLATEVAR_SCENARIO_NAME:[self.__get_rampup_scenario(), self.__get_main_scenario()]} | ||
|
Collaborator
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Note that in all three cases the template var is the default case. If the user doesn't explicitly specify a val via the CLI args we use the template var instead. |
||
|
|
||
| root["bindings"] = self.__build_bindings(self.table) | ||
|
|
||
|
|
@@ -185,4 +194,4 @@ def __build_schema(self): | |
| main_write_block = {"name":"main-write", "tags":{"phase":"main", "type":"write"}, "params":cl_ratio_map, "statements": [self.__build_main_write_statement()]} | ||
| root["blocks"] = [rampup_block, main_read_block, main_write_block] | ||
|
|
||
| return yaml.dump(root, default_flow_style=False) | ||
| return yaml.safe_dump(root, default_flow_style=False) | ||
|
Collaborator
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. We were seeing cases in which the YAML dump was writing a serialized Python Unicode string here which wound up with something like "!!python/unicode foo". PyYAML supports serializing arbitrary Python types; safe_dump() requires the output to be a base string, which is exactly what we want here. |
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -22,6 +22,20 @@ | |
|
|
||
| class SchemaTestMixin: | ||
|
|
||
| # Resource directory management logic | ||
| def cqlReferenceSchema(self, version): | ||
| return "tests/integration/resources/cql-schemas/{}.cql".format(version) | ||
|
|
||
|
|
||
| def nbReferenceYaml(self, version): | ||
| return "tests/integration/resources/nb-schemas/{}.yaml".format(version) | ||
|
|
||
|
|
||
| def nbBaseSchema(self): | ||
| return "tests/integration/resources/nb-base-schema.cql" | ||
|
Collaborator
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Some file cleanup. Patterns were developing in the tests around referencing base + expected CQL/YAML but many of the tests were still manipulating raw paths. Goal here is to consolidate that logic in the framework so that it only has to be implemented once. |
||
|
|
||
|
|
||
| # Temp dir logic | ||
| def basePath(self, name): | ||
| return os.path.join(self.dirs.basePath, name) | ||
|
|
||
|
|
@@ -45,6 +59,7 @@ def makeTempDirs(self): | |
| self.dirs = TempDirs(base, outputDir) | ||
|
|
||
|
|
||
| # Cassandra connection logic | ||
| def connectToLocalCassandra(self): | ||
| session = None | ||
| while not session: | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,43 @@ | ||
| import glob | ||
| import logging | ||
| import os | ||
| import sys | ||
|
|
||
| try: | ||
| import unittest2 as unittest | ||
| except ImportError: | ||
| import unittest | ||
|
|
||
| if os.name == 'posix' and sys.version_info[0] < 3: | ||
| import subprocess32 as subprocess | ||
| else: | ||
| import subprocess | ||
|
|
||
| from tests.integration import SchemaTestMixin | ||
| from tests.integration.nb import ExportNbMixin | ||
|
|
||
| log = logging.getLogger('adelphi') | ||
|
|
||
| class TestNbExportOutputDirTemplateVars(unittest.TestCase, SchemaTestMixin, ExportNbMixin): | ||
|
|
||
| def setUp(self): | ||
| super(TestNbExportOutputDirTemplateVars, self).setUp() | ||
|
|
||
|
|
||
| def getBaseSchemaPath(self): | ||
| return self.nbBaseSchema() | ||
|
|
||
|
|
||
| def runAdelphi(self, version=None): | ||
| stderrPath = self.stderrPath(version) | ||
| outputDirPath = self.outputDirPath(version) | ||
| os.mkdir(outputDirPath) | ||
| cmdStr = "adelphi --output-dir={} export-nb 2>> {}" | ||
| subprocess.run(cmdStr.format(outputDirPath, stderrPath), shell=True) | ||
|
|
||
|
|
||
| def evalAdelphiOutput(self, version=None): | ||
| outputDirPath = self.outputDirPath(version) | ||
| outputSchemas = glob.glob("{}/*/schema".format(outputDirPath)) | ||
| self.assertEqual(len(outputSchemas), 1, "Export of nosqlbench config only supports a single keyspace") | ||
| self.compareToReferenceYaml(self.nbReferenceYaml("{}-templatevars".format(version)), outputSchemas[0]) |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,39 @@ | ||
| import logging | ||
| import os | ||
| import sys | ||
|
|
||
| try: | ||
| import unittest2 as unittest | ||
| except ImportError: | ||
| import unittest | ||
|
|
||
| if os.name == 'posix' and sys.version_info[0] < 3: | ||
| import subprocess32 as subprocess | ||
| else: | ||
| import subprocess | ||
|
|
||
| from tests.integration import SchemaTestMixin | ||
| from tests.integration.nb import ExportNbMixin | ||
|
|
||
| log = logging.getLogger('adelphi') | ||
|
|
||
| class TestNbExportStdoutTemplateVars(unittest.TestCase, SchemaTestMixin, ExportNbMixin): | ||
|
|
||
| def setUp(self): | ||
| super(TestNbExportStdoutTemplateVars, self).setUp() | ||
|
|
||
|
|
||
| def getBaseSchemaPath(self): | ||
| return self.nbBaseSchema() | ||
|
|
||
|
|
||
| def runAdelphi(self, version=None): | ||
| stdoutPath = self.stdoutPath(version) | ||
| stderrPath = self.stderrPath(version) | ||
| cmdStr = "adelphi export-nb > {} 2>> {}" | ||
| subprocess.run(cmdStr.format(stdoutPath, stderrPath), shell=True) | ||
|
|
||
|
|
||
| def evalAdelphiOutput(self, version=None): | ||
| self.maxDiff = None | ||
| self.compareToReferenceYaml(self.nbReferenceYaml("{}-templatevars".format(version)), self.stdoutPath(version)) |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,43 @@ | ||
| bindings: | ||
| key1_dist: Hash(); Mod(1000000000); ToString() -> String | ||
| key1_seq: Mod(1000000000); ToString() -> String | ||
| key2_dist: Hash(); Mod(1000000000); ToString() -> String | ||
| key2_seq: Mod(1000000000); ToString() -> String | ||
| value_dist: Hash(); Mod(1000000000); ToString() -> String | ||
| blocks: | ||
| - name: rampup | ||
| params: | ||
| cl: LOCAL_QUORUM | ||
| statements: | ||
| - rampup-insert: insert into "testkeyspace"."testtable" ("key1","key2","value") | ||
| values ({key1_seq},{key2_seq},{value_dist}) | ||
| tags: | ||
| name: rampup-insert | ||
| tags: | ||
| phase: rampup | ||
| - name: main-read | ||
| params: &id001 | ||
| cl: LOCAL_QUORUM | ||
| ratio: 5 | ||
| statements: | ||
| - main-select: select * from "testkeyspace"."testtable" where "key1" = {key1_dist} | ||
| and "key2" = {key2_dist} | ||
| tags: | ||
| name: main-select | ||
| tags: | ||
| phase: main | ||
| type: read | ||
| - name: main-write | ||
| params: *id001 | ||
| statements: | ||
| - main-insert: insert into "testkeyspace"."testtable" ("key1","key2","value") values | ||
| ({key1_seq},{key2_seq},{value_dist}) | ||
| tags: | ||
| name: main-insert | ||
| tags: | ||
| phase: main | ||
| type: write | ||
| scenarios: | ||
| TEMPLATE(scenarioname,default): | ||
| - run driver=cql tags=phase:rampup cycles=TEMPLATE(rampup-cycles,1000) threads=auto | ||
| - run driver=cql tags=phase:main cycles=TEMPLATE(main-cycles,1000) threads=auto |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just a bit of cleanup... apparently this wasn't used anymore