merge from main

This commit is contained in:
Kenneth Kehl
2024-08-12 07:15:46 -07:00
8 changed files with 40 additions and 24 deletions

View File

@@ -14,14 +14,14 @@
document.getElementById('message').innerText = `${sms_sent.toLocaleString()} sent / ${sms_remaining_messages.toLocaleString()} remaining`; document.getElementById('message').innerText = `${sms_sent.toLocaleString()} sent / ${sms_remaining_messages.toLocaleString()} remaining`;
// Calculate minimum width for "Messages Sent" as 1% of the total chart width // Calculate minimum width for "Messages Sent" as 1% of the total chart width
var minSentPercentage = 0.01; // Minimum width as a percentage of total messages (1% in this case) var minSentPercentage = 0.02; // Minimum width as a percentage of total messages (1% in this case)
var minSentValue = totalMessages * minSentPercentage; var minSentValue = totalMessages * minSentPercentage;
var displaySent = Math.max(sms_sent, minSentValue); var displaySent = Math.max(sms_sent, minSentValue);
var displayRemaining = totalMessages - displaySent; var displayRemaining = totalMessages - displaySent;
var svg = d3.select("#totalMessageChart"); var svg = d3.select("#totalMessageChart");
var width = chartContainer.clientWidth; var width = chartContainer.clientWidth;
var height = 64; var height = 48;
// Ensure the width is set correctly // Ensure the width is set correctly
if (width === 0) { if (width === 0) {
@@ -62,7 +62,7 @@
.attr("x", 0) // Initially set to 0, will be updated during animation .attr("x", 0) // Initially set to 0, will be updated during animation
.attr("y", 0) .attr("y", 0)
.attr("height", height) .attr("height", height)
.attr("fill", '#fa9441') .attr("fill", '#C7CACE')
.attr("width", 0) // Start with width 0 for animation .attr("width", 0) // Start with width 0 for animation
.on('mouseover', function(event) { .on('mouseover', function(event) {
tooltip.style('display', 'block') tooltip.style('display', 'block')

View File

@@ -2,7 +2,7 @@
$delivered: color('blue-50v'); $delivered: color('blue-50v');
$pending: color('green-cool-40v'); $pending: color('green-cool-40v');
$failed: color('orange-30v'); $failed: color('gray-cool-20');
.chart-container { .chart-container {
display: flex; display: flex;
@@ -11,6 +11,10 @@ $failed: color('orange-30v');
} }
} }
#totalMessageChartContainer {
max-width: 600px;
}
.bar { .bar {
border-radius: units(0.5); border-radius: units(0.5);
&.delivered, &.usage { &.delivered, &.usage {

View File

@@ -56,6 +56,9 @@ class NotifyAdminAPIClient(BaseAPIClient):
): ):
abort(403) abort(403)
def is_calling_signin_url(self, arg):
return arg.startswith("('/user")
def check_inactive_user(self, *args): def check_inactive_user(self, *args):
still_signing_in = False still_signing_in = False
@@ -64,14 +67,7 @@ class NotifyAdminAPIClient(BaseAPIClient):
# and we only want to check the first arg # and we only want to check the first arg
for arg in args: for arg in args:
arg = str(arg) arg = str(arg)
if ( if self.is_calling_signin_url(arg):
"get-login-gov-user" in arg
or "user/email" in arg
or "/activate" in arg
or "/email-code" in arg
or "/verify/code" in arg
or "/user" in arg
):
still_signing_in = True still_signing_in = True
# This seems to be a weird edge case that happens intermittently with invites # This seems to be a weird edge case that happens intermittently with invites

View File

@@ -28,10 +28,6 @@
<div id="message"></div> <div id="message"></div>
</div> </div>
<div id="totalMessageTable" class="margin-0"></div> <div id="totalMessageTable" class="margin-0"></div>
<p class="align-with-heading-copy margin-bottom-4">
What counts as 1 text message part?<br />
See <a class="usa-link" href="{{ url_for('.pricing') }}">Tracking usage</a>.
</p>
<h2 class="line-height-sans-2 margin-bottom-0 margin-top-4"> <h2 class="line-height-sans-2 margin-bottom-0 margin-top-4">
Activity snapshot Activity snapshot

10
poetry.lock generated
View File

@@ -201,13 +201,13 @@ crt = ["botocore[crt] (>=1.21.0,<2.0a0)"]
[[package]] [[package]]
name = "botocore" name = "botocore"
version = "1.34.150" version = "1.34.156"
description = "Low-level, data-driven core of boto 3." description = "Low-level, data-driven core of boto 3."
optional = false optional = false
python-versions = ">=3.8" python-versions = ">=3.8"
files = [ files = [
{file = "botocore-1.34.150-py3-none-any.whl", hash = "sha256:b988d47f4d502df85befce11a48002421e4e6ea4289997b5e0261bac5fa76ce6"}, {file = "botocore-1.34.156-py3-none-any.whl", hash = "sha256:c48f8c8996216dfdeeb0aa6d3c0f2c7ae25234766434a2ea3e57bdc08494bdda"},
{file = "botocore-1.34.150.tar.gz", hash = "sha256:4d23387e0f076d87b637a2a35c0ff2b8daca16eace36b63ce27f65630c6b375a"}, {file = "botocore-1.34.156.tar.gz", hash = "sha256:5d1478c41ab9681e660b3322432fe09c4055759c317984b7b8d3af9557ff769a"},
] ]
[package.dependencies] [package.dependencies]
@@ -216,7 +216,7 @@ python-dateutil = ">=2.1,<3.0.0"
urllib3 = {version = ">=1.25.4,<2.2.0 || >2.2.0,<3", markers = "python_version >= \"3.10\""} urllib3 = {version = ">=1.25.4,<2.2.0 || >2.2.0,<3", markers = "python_version >= \"3.10\""}
[package.extras] [package.extras]
crt = ["awscrt (==0.20.11)"] crt = ["awscrt (==0.21.2)"]
[[package]] [[package]]
name = "cachecontrol" name = "cachecontrol"
@@ -3088,4 +3088,4 @@ files = [
[metadata] [metadata]
lock-version = "2.0" lock-version = "2.0"
python-versions = "^3.12.2" python-versions = "^3.12.2"
content-hash = "b271104f669ce0a8e78fb09299b61cf0502cc81a18213dda00f77c759b6e0209" content-hash = "9d6309a76755b2639d787f99944c1ead0bd93ab9f2f13208f88c51cecb5e0081"

View File

@@ -39,7 +39,7 @@ markdown = "^3.5.2"
async-timeout = "^4.0.3" async-timeout = "^4.0.3"
bleach = "^6.1.0" bleach = "^6.1.0"
boto3 = "^1.34.150" boto3 = "^1.34.150"
botocore = "^1.34.150" botocore = "^1.34.156"
cachetools = "^5.4.0" cachetools = "^5.4.0"
cffi = "^1.16.0" cffi = "^1.16.0"
cryptography = "^43.0.0" cryptography = "^43.0.0"

View File

@@ -41,6 +41,26 @@ def test_active_service_can_be_modified(notify_admin, method, user, service):
assert ret == request.return_value assert ret == request.return_value
@pytest.mark.parametrize(
("arg", "expected_result"),
[
(
"('/user/c5f8a5c9-56d5-4fa9-8c30-3449ae10c072/verify/code',)",
True,
),
("('/user/get-login-gov-user',)", True),
(
"('/service/blahblahblah',)",
False,
),
],
)
def test_is_calling_signin_url(arg, expected_result):
api_client = NotifyAdminAPIClient()
result = api_client.is_calling_signin_url(arg)
assert result == expected_result
@pytest.mark.parametrize("method", ["put", "post", "delete"]) @pytest.mark.parametrize("method", ["put", "post", "delete"])
def test_inactive_service_cannot_be_modified_by_normal_user( def test_inactive_service_cannot_be_modified_by_normal_user(
notify_admin, api_user_active, method notify_admin, api_user_active, method

View File

@@ -57,7 +57,7 @@ test('SVG element is correctly set up', done => {
setTimeout(() => { setTimeout(() => {
const svg = document.getElementById('totalMessageChart'); const svg = document.getElementById('totalMessageChart');
expect(svg.getAttribute('width')).toBe('600'); expect(svg.getAttribute('width')).toBe('600');
expect(svg.getAttribute('height')).toBe('64'); expect(svg.getAttribute('height')).toBe('48');
done(); done();
}, 1000); // Ensure enough time for the DOM updates }, 1000); // Ensure enough time for the DOM updates
}); });
@@ -159,7 +159,7 @@ test('SVG bars are created and animated correctly', done => {
// Initial check // Initial check
const sentBar = svg.querySelector('rect[fill="#0076d6"]'); const sentBar = svg.querySelector('rect[fill="#0076d6"]');
const remainingBar = svg.querySelector('rect[fill="#fa9441"]'); const remainingBar = svg.querySelector('rect[fill="#C7CACE"]');
expect(sentBar).not.toBeNull(); expect(sentBar).not.toBeNull();
expect(remainingBar).not.toBeNull(); expect(remainingBar).not.toBeNull();