forked from mysql-net/MySqlConnector
-
Notifications
You must be signed in to change notification settings - Fork 5
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Summary: We will use S2MS for testing on Windows Test Plan: https://app.circleci.com/pipelines/github/memsql/SingleStoreNETConnector/142/workflows/2edb516a-e9a0-4325-bf66-bdc340c80a59 Reviewers: mshcherbina-ua, okramarenko-ua Reviewed By: mshcherbina-ua Subscribers: engineering-list JIRA Issues: PLAT-6093 Differential Revision: https://grizzly.internal.memcompute.com/D54941
- Loading branch information
Pavlo
committed
Feb 17, 2022
1 parent
787e720
commit 39b090b
Showing
6 changed files
with
241 additions
and
6 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,6 +1,6 @@ | ||
{ | ||
"Data": { | ||
"ConnectionString": "server=127.0.0.1;user id=SQL_USER_NAME;password=SQL_USER_PASSWORD;port=3306;database=singlestoretest", | ||
"ConnectionString": "server=SINGLESTORE_HOST;user id=SQL_USER_NAME;password=SQL_USER_PASSWORD;port=3306;database=singlestoretest", | ||
"UnsupportedFeatures": "CachingSha2Password,Ed25519,QueryAttributes,Tls11,Tls13,UuidToBin,UnixDomainSocket,Sha256Password,GlobalLog" | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -4,9 +4,12 @@ parameters: | |
type: string | ||
default: "1.0.0" | ||
|
||
orbs: | ||
win: circleci/[email protected] | ||
|
||
commands: | ||
setup-environment-ubuntu: | ||
description: "Setup the linux environment" | ||
description: Setup Linux environment | ||
steps: | ||
- run: | ||
name: Install .NET Core 6.0 | ||
|
@@ -20,8 +23,52 @@ commands: | |
sudo apt-get install -y mariadb-client-core-10.3 | ||
sudo apt-get install -y dotnet-sdk-6.0 | ||
dotnet --info | ||
run-tests-win: | ||
description: Run tests on Windows | ||
parameters: | ||
target_framework: | ||
type: string | ||
steps: | ||
- run: | ||
name: Unit tests | ||
command: | | ||
cd tests\MySqlConnector.Tests | ||
dotnet.exe test -f << parameters.target_framework >> -c Release --no-build | ||
cd ..\.. | ||
- run: | ||
name: Conformance tests | ||
command: | | ||
cd tests/Conformance.Tests/ | ||
dotnet.exe test -f << parameters.target_framework >> -c Release --no-build | ||
cd ..\.. | ||
- run: | ||
name: SideBySide tests | ||
command: | | ||
cd tests\SideBySide | ||
dotnet.exe test -f << parameters.target_framework >> -c Release --no-build | ||
cd ..\.. | ||
jobs: | ||
test-windows: | ||
executor: win/default | ||
steps: | ||
- checkout | ||
- run: | ||
name: Build project binaries | ||
command: | | ||
choco upgrade dotnet-sdk | ||
dotnet.exe build -c Release | ||
- run: | ||
name: Start SingleStore for SideBySide tests | ||
command: | | ||
pip install pymysql | ||
python.exe .circleci\s2ms_cluster.py start singlestoretest | ||
- run: | ||
name: Fill test config | ||
command: python.exe .circleci\fill_test_config.py | ||
- run-tests-win: | ||
target_framework: net6.0 | ||
|
||
test-ubuntu: | ||
parameters: | ||
singlestore_image: | ||
|
@@ -46,25 +93,27 @@ jobs: | |
name: Copy config file for SideBySide tests | ||
command: | | ||
cp ./.circleci/SideBySide/config.json tests/SideBySide/config.json | ||
sed -i "s|SINGLESTORE_HOST|127.0.0.1|g" tests/SideBySide/config.json | ||
sed -i "s|SQL_USER_PASSWORD|${SQL_USER_PASSWORD}|g" tests/SideBySide/config.json | ||
sed -i "s|SQL_USER_NAME|root|g" tests/SideBySide/config.json | ||
cp tests/SideBySide/config.json tests/SideBySide/bin/Release/net6.0/config.json | ||
- run: | ||
name: Unit tests | ||
command: | | ||
cd tests/MySqlConnector.Tests | ||
dotnet test -f net6.0 -c Release | ||
dotnet test -f net6.0 -c Release --no-build | ||
cd ../../ | ||
- run: | ||
name: Conformance tests | ||
command: | | ||
cd tests/Conformance.Tests/ | ||
dotnet test -f net6.0 -c Release | ||
dotnet test -f net6.0 -c Release --no-build | ||
cd ../../ | ||
- run: | ||
name: SideBySide tests | ||
command: | | ||
cd tests/SideBySide | ||
dotnet test -f net6.0 -c Release | ||
dotnet test -f net6.0 -c Release --no-build | ||
cd ../../ | ||
workflows: | ||
|
@@ -89,3 +138,5 @@ workflows: | |
parameters: | ||
singlestore_image: | ||
- singlestore/cluster-in-a-box:centos-7.3.13-761e3259b3-3.2.11-1.11.9 | ||
- test-windows: | ||
name: Test S2MS on Windows |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,35 @@ | ||
import json | ||
import os | ||
|
||
|
||
CLUSTER_ID_FILE = "CLUSTER_ID" | ||
HOSTNAME_TMPL = "svc-{}-ddl.aws-frankfurt-1.svc.singlestore.com" | ||
|
||
NET_FRAMEWORKS = ["net452", "net461", "net472", "netcoreapp3.1", "net5.0", "net6.0"] | ||
|
||
|
||
if __name__ == "__main__": | ||
|
||
home_dir = os.getenv("HOMEPATH") | ||
if home_dir is None: | ||
home_dir = os.getenv("HOME") | ||
|
||
with open(CLUSTER_ID_FILE, "r") as f: | ||
cluster_id = f.read().strip() | ||
|
||
hostname = HOSTNAME_TMPL.format(cluster_id) | ||
password = os.getenv("SQL_USER_PASSWORD") | ||
|
||
with open("./.circleci/SideBySide/config.json", "r") as f_in: | ||
config_content = f_in.read() | ||
|
||
config_content = config_content.replace("SINGLESTORE_HOST", hostname, 1) | ||
config_content = config_content.replace("SQL_USER_PASSWORD", password, 1) | ||
config_content = config_content.replace("SQL_USER_NAME", "admin", 1) | ||
|
||
for target_framework in NET_FRAMEWORKS: | ||
with open(f"tests/SideBySide/bin/Release/{target_framework}/config.json", "w") as f_out: | ||
f_out.write(config_content) | ||
|
||
with open(os.path.join(home_dir, "CONNECTION_STRING"), "w") as f_conn: | ||
f_conn.write(json.loads(config_content)["Data"]["ConnectionString"]) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,134 @@ | ||
import json | ||
import os | ||
import pymysql | ||
import requests | ||
from requests.adapters import HTTPAdapter | ||
import sys | ||
from time import sleep | ||
from typing import Dict, Optional | ||
from urllib3 import Retry | ||
|
||
BASE_URL = "https://api.singlestore.com" | ||
CLUSTERS_PATH = "/v0beta/clusters" | ||
|
||
SQL_USER_PASSWORD = os.getenv("SQL_USER_PASSWORD") # project UI env-var reference | ||
S2MS_API_KEY = os.getenv("S2MS_API_KEY") # project UI env-var reference | ||
|
||
HEADERS = { | ||
"Authorization": f"Bearer {S2MS_API_KEY}", | ||
"Content-Type": "application/json", | ||
"Accept": "application/json" | ||
} | ||
|
||
CLUSTER_NAME = ".NET-connector-ci-test-cluster" | ||
AWS_EU_CENTRAL_REGION = "7e7ffd27-20f7-44b6-87e6-e72828a81ac7" | ||
AUTO_TERMINATE_MINUTES = 30 | ||
|
||
PAYLOAD_FOR_CREATE = { | ||
"name": CLUSTER_NAME, | ||
"regionID": AWS_EU_CENTRAL_REGION, | ||
"adminPassword": SQL_USER_PASSWORD, | ||
"expiresAt": f"{AUTO_TERMINATE_MINUTES}m", | ||
"firewallRanges": [ | ||
"0.0.0.0/0" | ||
], | ||
"size": "S-00" | ||
} | ||
HOSTNAME_TMPL = "svc-{}-ddl.aws-frankfurt-1.svc.singlestore.com" | ||
CLUSTER_ID_FILE = "CLUSTER_ID" | ||
|
||
TOTAL_RETRIES = 5 | ||
S2MS_REQUEST_TIMEOUT = 60 | ||
|
||
|
||
def request_with_retry(request_method, url, data=None, headers=HEADERS): | ||
try: | ||
with requests.Session() as s: | ||
retries = Retry( | ||
total=TOTAL_RETRIES, | ||
backoff_factor=0.2, | ||
status_forcelist=[500, 502, 503, 504]) | ||
|
||
s.mount('http://', HTTPAdapter(max_retries=retries)) | ||
s.mount('https://', HTTPAdapter(max_retries=retries)) | ||
|
||
return s.request(request_method, url, data=data, headers=headers, timeout=S2MS_REQUEST_TIMEOUT) | ||
except requests.exceptions.RequestException as e: | ||
raise SystemExit(e) | ||
|
||
|
||
def create_cluster() -> str: | ||
cl_id = request_with_retry("POST", BASE_URL + CLUSTERS_PATH, data=json.dumps(PAYLOAD_FOR_CREATE)) | ||
return cl_id.json()["clusterID"] | ||
|
||
|
||
def get_cluster_info(cluster_id: str) -> Dict: | ||
cl_id = request_with_retry("GET", BASE_URL + CLUSTERS_PATH + f"/{cluster_id}") | ||
return cl_id.json() | ||
|
||
|
||
def is_cluster_active(cluster_id: str) -> bool: | ||
cl_info = get_cluster_info(cluster_id) | ||
return cl_info["state"] == "Active" | ||
|
||
|
||
def wait_start(cluster_id: str) -> None: | ||
print(f"Waiting for cluster {cluster_id} to be available for connection..", end="", flush=True) | ||
time_wait = 0 | ||
while (not is_cluster_active(cluster_id) and time_wait < 600): | ||
print(".", end="", flush=True) | ||
sleep(5) | ||
time_wait += 5 | ||
if time_wait < 600: | ||
print("\nCluster is active!") | ||
else: | ||
print(f"\nTimeout error: can't connect to {cluster_id} for more than 10 minutes!") | ||
|
||
|
||
def terminate_cluster(cluster_id: str) -> None: | ||
request_with_retry("DELETE", BASE_URL + CLUSTERS_PATH + f"/{cluster_id}") | ||
|
||
|
||
def check_connection(cluster_id: str, create_db: Optional[str] = None): | ||
conn = pymysql.connect( | ||
user="admin", | ||
password=SQL_USER_PASSWORD, | ||
host=HOSTNAME_TMPL.format(cluster_id), | ||
port=3306) | ||
|
||
cur = conn.cursor() | ||
try: | ||
cur.execute("SELECT NOW():>TEXT") | ||
res = cur.fetchall() | ||
print(f"Successfully connected to {cluster_id} at {res[0][0]}") | ||
|
||
if create_db is not None: | ||
cur.execute(f"DROP DATABASE IF EXISTS {create_db}") | ||
cur.execute(f"CREATE DATABASE {create_db}") | ||
finally: | ||
cur.close() | ||
conn.close() | ||
|
||
|
||
if __name__ == "__main__": | ||
if len(sys.argv) < 2: | ||
print("Not enough arguments to start/terminate cluster!") | ||
exit(1) | ||
command = sys.argv[1] | ||
db_name = None | ||
if len(sys.argv) > 2: | ||
db_name = sys.argv[2] | ||
|
||
if command == "start": | ||
new_cl_id = create_cluster() | ||
with open(CLUSTER_ID_FILE, "w") as f: | ||
f.write(new_cl_id) | ||
wait_start(new_cl_id) | ||
check_connection(new_cl_id, db_name) | ||
exit(0) | ||
|
||
if command == "terminate": | ||
with open(CLUSTER_ID_FILE, "r") as f: | ||
cl_id = f.read() | ||
terminate_cluster(cl_id) | ||
exit(0) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters