Skip to content

Commit

Permalink
Merge pull request #427 from DalgoT4D/minor-usage-error-fix
Browse files Browse the repository at this point in the history
maintaining single set of usage dashboard creds for all orgs
  • Loading branch information
fatchat authored Jan 9, 2024
2 parents e6ab242 + eb2c59a commit 4bf6056
Show file tree
Hide file tree
Showing 7 changed files with 46 additions and 37 deletions.
1 change: 1 addition & 0 deletions .env.template
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@ SENDGRID_YOUVE_BEEN_ADDED_TEMPLATE=
PREFECT_NOTIFICATIONS_WEBHOOK_KEY=

SUPERSET_USAGE_DASHBOARD_API_URL=
SUPERSET_USAGE_CREDS_SECRET_ID=



Expand Down
15 changes: 14 additions & 1 deletion ddpui/api/superset_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -63,9 +63,22 @@ def post_fetch_embed_token(request, dashboard_uuid): # pylint: disable=unused-a
if warehouse is None:
raise HttpError(400, "create a warehouse first")

if orguser.org.viz_url is None:
raise HttpError(
400,
"your superset subscription is not active, please contact the Dalgo team",
)

superset_creds = os.getenv("SUPERSET_USAGE_CREDS_SECRET_ID")
if superset_creds is None:
raise HttpError(
400,
"superset usage credentials are missing",
)

# {username: "", password: "", first_name: "", last_name: ""} # skipcq: PY-W0069
credentials = secretsmanager.retrieve_superset_usage_dashboard_credentials(
warehouse
superset_creds
)
if credentials is None:
raise HttpError(400, "superset usage credentials are missing")
Expand Down
16 changes: 2 additions & 14 deletions ddpui/management/commands/createsupersetusageuser.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,25 +26,13 @@ def add_arguments(self, parser): # skipcq: PYL-R0201
parser.add_argument("--password", required=True)

def handle(self, *args, **options):
"""adds credentials to secrets manager"""
org = Org.objects.filter(slug=options["org"]).first()
if not org:
logger.error("org not found")
return
warehouse = OrgWarehouse.objects.filter(org=org).first()
if not warehouse:
logger.error("warehouse not found")
return

"""adds superset credentials to secrets manager"""
secret_id = save_superset_usage_dashboard_credentials(
warehouse,
{
"username": options["username"],
"first_name": options["first_name"],
"last_name": options["last_name"],
"password": options["password"],
},
)
warehouse.superset_creds = secret_id
warehouse.save()
logger.info("credentials saved")
logger.info(f"credentials saved to secretId = {secret_id}")
16 changes: 16 additions & 0 deletions ddpui/migrations/0039_remove_orgwarehouse_superset_creds.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
# Generated by Django 4.1.7 on 2024-01-09 07:44

from django.db import migrations


class Migration(migrations.Migration):
dependencies = [
("ddpui", "0038_org_is_demo"),
]

operations = [
migrations.RemoveField(
model_name="orgwarehouse",
name="superset_creds",
),
]
3 changes: 0 additions & 3 deletions ddpui/models/org.py
Original file line number Diff line number Diff line change
Expand Up @@ -130,9 +130,6 @@ class OrgWarehouse(models.Model):
airbyte_norm_op_id = models.TextField( # skipcq: PTC-W0901, PTC-W0906
max_length=36, null=True
)
superset_creds = models.CharField( # skipcq: PTC-W0901, PTC-W0906
max_length=200, null=True
)

def __str__(self) -> str:
return (
Expand Down
14 changes: 5 additions & 9 deletions ddpui/tests/helper/test_secretsmanager.py
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,9 @@ def test_generate_warehouse_credentials_name():

@patch("ddpui.utils.secretsmanager.uuid4", Mock(return_value="unique-val"))
def test_generate_superset_credentials_name():
org = Org(name="temporg", slug="temporg")
response = generate_superset_credentials_name(org)
assert response == "supersetCreds-temporg-unique-val"
response = generate_superset_credentials_name()
assert response == "supersetCreds-unique-val"
assert response.startswith("supersetCreds")


@patch(
Expand Down Expand Up @@ -133,10 +133,7 @@ def test_delete_warehouse_credentials(
def test_save_superset_usage_dashboard_credentials(mock_getclient: Mock):
create_secret_mock = Mock(return_value={"Name": "supersetcreds"})
mock_getclient.return_value = Mock(create_secret=create_secret_mock)
warehouse = Mock(org=Mock())
response = save_superset_usage_dashboard_credentials(
warehouse, {"credkey": "credval"}
)
response = save_superset_usage_dashboard_credentials({"credkey": "credval"})
assert response == "supersetcreds"
create_secret_mock.assert_called_once_with(
Name="supersetcreds", SecretString='{"credkey": "credval"}'
Expand All @@ -149,6 +146,5 @@ def test_retrieve_superset_usage_dashboard_credentials(
):
get_secret_value = Mock(return_value={"SecretString": '{"credkey": "credval"}'})
mock_getclient.return_value = Mock(get_secret_value=get_secret_value)
warehouse = Mock(superset_creds="credentialskey")
retrieve_superset_usage_dashboard_credentials(warehouse)
retrieve_superset_usage_dashboard_credentials("credentialskey")
get_secret_value.assert_called_once_with(SecretId="credentialskey")
18 changes: 8 additions & 10 deletions ddpui/utils/secretsmanager.py
Original file line number Diff line number Diff line change
Expand Up @@ -99,9 +99,9 @@ def generate_warehouse_credentials_name(org: Org):
return f"warehouseCreds-{org.slug}-{uuid4()}"


def generate_superset_credentials_name(org: Org):
def generate_superset_credentials_name():
"""store the connection credentials to their data warehouse"""
return f"supersetCreds-{org.slug}-{uuid4()}"
return f"supersetCreds-{uuid4()}"


def save_github_token(org: Org, access_token: str):
Expand Down Expand Up @@ -196,12 +196,10 @@ def delete_warehouse_credentials(warehouse: OrgWarehouse) -> None:
pass


def save_superset_usage_dashboard_credentials(
warehouse: OrgWarehouse, credentials: dict
):
"""saves superset usage dashboard user credentials for an org under a predefined secret name"""
def save_superset_usage_dashboard_credentials(credentials: dict):
"""saves superset usage dashboard user credentials under a predefined secret name"""
aws_sm = get_client()
secret_name = generate_superset_credentials_name(warehouse.org)
secret_name = generate_superset_credentials_name()
response = aws_sm.create_secret(
Name=secret_name,
SecretString=json.dumps(credentials),
Expand All @@ -214,11 +212,11 @@ def save_superset_usage_dashboard_credentials(


def retrieve_superset_usage_dashboard_credentials(
warehouse: OrgWarehouse,
secret_id: str,
) -> dict | None:
"""decodes and returns the saved superset usage dashboard credentials for an org"""
"""decodes and returns the saved superset usage dashboard credentials"""
aws_sm = get_client()
response = aws_sm.get_secret_value(SecretId=warehouse.superset_creds)
response = aws_sm.get_secret_value(SecretId=secret_id)
return (
json.loads(response["SecretString"])
if response and "SecretString" in response
Expand Down

0 comments on commit 4bf6056

Please sign in to comment.