diff --git a/.github/workflows/deploy-demo.yml b/.github/workflows/deploy-demo.yml index bf9757493..57f11acf9 100644 --- a/.github/workflows/deploy-demo.yml +++ b/.github/workflows/deploy-demo.yml @@ -54,6 +54,7 @@ jobs: ADMIN_CLIENT_SECRET: ${{ secrets.ADMIN_CLIENT_SECRET }} NEW_RELIC_LICENSE_KEY: ${{ secrets.NEW_RELIC_LICENSE_KEY }} NR_BROWSER_KEY: ${{ secrets.NR_BROWSER_KEY }} + COMMIT_HASH: ${{ github.sha }} LOGIN_PEM: ${{ secrets.LOGIN_PEM }} LOGIN_DOT_GOV_CLIENT_ID: "urn:gov:gsa:openidconnect.profiles:sp:sso:gsa:notify-gov" LOGIN_DOT_GOV_USER_INFO_URL: "https://secure.login.gov/api/openid_connect/userinfo" @@ -75,6 +76,7 @@ jobs: --var ADMIN_CLIENT_SECRET="$ADMIN_CLIENT_SECRET" --var NEW_RELIC_LICENSE_KEY="$NEW_RELIC_LICENSE_KEY" --var NR_BROWSER_KEY="$NR_BROWSER_KEY" + --var COMMIT_HASH="$COMMIT_HASH" --var LOGIN_PEM="$LOGIN_PEM" --var LOGIN_DOT_GOV_CLIENT_ID="$LOGIN_DOT_GOV_CLIENT_ID" --var LOGIN_DOT_GOV_USER_INFO_URL="$LOGIN_DOT_GOV_USER_INFO_URL" diff --git a/.github/workflows/deploy-prod.yml b/.github/workflows/deploy-prod.yml index a0aaa81c5..3e169cdc9 100644 --- a/.github/workflows/deploy-prod.yml +++ b/.github/workflows/deploy-prod.yml @@ -54,6 +54,7 @@ jobs: ADMIN_CLIENT_SECRET: ${{ secrets.ADMIN_CLIENT_SECRET }} NEW_RELIC_LICENSE_KEY: ${{ secrets.NEW_RELIC_LICENSE_KEY }} NR_BROWSER_KEY: ${{ secrets.NR_BROWSER_KEY }} + COMMIT_HASH: ${{ github.sha }} LOGIN_PEM: ${{ secrets.LOGIN_PEM }} LOGIN_DOT_GOV_CLIENT_ID: "urn:gov:gsa:openidconnect.profiles:sp:sso:gsa:notify-gov" LOGIN_DOT_GOV_USER_INFO_URL: "https://secure.login.gov/api/openid_connect/userinfo" @@ -75,6 +76,7 @@ jobs: --var ADMIN_CLIENT_SECRET="$ADMIN_CLIENT_SECRET" --var NEW_RELIC_LICENSE_KEY="$NEW_RELIC_LICENSE_KEY" --var NR_BROWSER_KEY="$NR_BROWSER_KEY" + --var COMMIT_HASH="$COMMIT_HASH" --var LOGIN_PEM="$LOGIN_PEM" --var LOGIN_DOT_GOV_CLIENT_ID="$LOGIN_DOT_GOV_CLIENT_ID" --var LOGIN_DOT_GOV_USER_INFO_URL="$LOGIN_DOT_GOV_USER_INFO_URL" diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 915994d58..f620bd662 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -60,6 +60,7 @@ jobs: ADMIN_CLIENT_SECRET: ${{ secrets.ADMIN_CLIENT_SECRET }} NEW_RELIC_LICENSE_KEY: ${{ secrets.NEW_RELIC_LICENSE_KEY }} NR_BROWSER_KEY: ${{ secrets.NR_BROWSER_KEY }} + COMMIT_HASH: ${{ github.sha }} LOGIN_PEM: ${{ secrets.LOGIN_PEM }} LOGIN_DOT_GOV_CLIENT_ID: "urn:gov:gsa:openidconnect.profiles:sp:sso:gsa:notify-gov" LOGIN_DOT_GOV_USER_INFO_URL: "https://secure.login.gov/api/openid_connect/userinfo" @@ -81,6 +82,7 @@ jobs: --var ADMIN_CLIENT_SECRET="$ADMIN_CLIENT_SECRET" --var NEW_RELIC_LICENSE_KEY="$NEW_RELIC_LICENSE_KEY" --var NR_BROWSER_KEY="$NR_BROWSER_KEY" + --var COMMIT_HASH="$COMMIT_HASH" --var LOGIN_PEM="$LOGIN_PEM" --var LOGIN_DOT_GOV_CLIENT_ID="$LOGIN_DOT_GOV_CLIENT_ID" --var LOGIN_DOT_GOV_USER_INFO_URL="$LOGIN_DOT_GOV_USER_INFO_URL" diff --git a/README.md b/README.md index bbf9065db..5723047f2 100644 --- a/README.md +++ b/README.md @@ -251,7 +251,7 @@ pyenv virtualenv 3.12.2 notify-admin pyenv local notify-admin ``` -_If you're not sure which version of Python was installed with `pyenv`, you can check by running `pyenv versions` and it'll list everything available currently.You should see the virtual environment name in terminal as 'notify-admin'._ +_If you're not sure which version of Python was installed with `pyenv`, you can check by running `pyenv versions` and it'll list everything available currently._ Now [log into cloud.gov](https://cloud.gov/docs/getting-started/setup/#set-up-the-command-line) in the command line by using this command: @@ -276,26 +276,27 @@ project-specific environment variables. ### Switching to different environment -Once all of pre-requisites for the project are installed and to switch to newer environment with newer python version follow the below steps to create new virtual environment. +Once all of pre-requisites for the project are installed and for first time setup or if you're upgrading an existing project to newer environment with newer python version follow below steps to create new virtual environment. -First install the newer Python version we need with `pyenv`, (say the planned upgrade to 3.15) like so : +First install the newer Python version we need with `pyenv`, (say the planned upgrade to 3.12) like so : ```sh -pyenv install 3.15 +pyenv install 3.12 ``` -Now go into the project directory (`notifications-api` by default), create a +Now go into the project directory (`notifications-admin` by default), create a virtual environment, and set the local Python version to point to the virtual -environment (assumes version Python `3.15.2` is what is installed on your +environment (assumes version Python `3.12.2` is what is installed on your machine): ```sh -cd notifications-api -pyenv virtualenv 3.15.2 notify-admin-upgrade +cd notifications-admin +pyenv virtualenv 3.12.2 notify-admin-upgrade pyenv local notify-admin-upgrade ``` -_If you're not sure which version of Python was installed with `pyenv`, you can check by running `pyenv versions` and it'll list everything available currently.you can deactivate the current environment by running `source deactivate` or `deactivate`.Close the terminal and reopen a new terminal should see the newer virtual environment name in terminal as 'notify-admin-upgrade'. you can the get python version ,executable, and other details for this environment by running `poetry env info`._ +_If you're not sure which version of Python was installed with `pyenv`, you can check by running `pyenv versions` and it'll list everything available currently.You can deactivate the current environment by running `source deactivate` or `deactivate`.Close the shell session and reopen a new shell session should show the newer virtual environment._ +_You can get version,executable, and other details for any environment by running `poetry env info`._ #### Updating the .env file for E2E tests diff --git a/app/assets/error_pages/5xx.html b/app/assets/error_pages/5xx.html index 48cbe9e61..d9d58530f 100644 --- a/app/assets/error_pages/5xx.html +++ b/app/assets/error_pages/5xx.html @@ -22,7 +22,7 @@ - + @@ -107,4 +107,4 @@ - \ No newline at end of file + diff --git a/app/assets/images/android-chrome-192x192.png b/app/assets/images/android-chrome-192x192.png index 6eaf9fa46..a1e8670ca 100644 Binary files a/app/assets/images/android-chrome-192x192.png and b/app/assets/images/android-chrome-192x192.png differ diff --git a/app/assets/images/android-chrome-256x256.png b/app/assets/images/android-chrome-256x256.png new file mode 100644 index 000000000..40c599492 Binary files /dev/null and b/app/assets/images/android-chrome-256x256.png differ diff --git a/app/assets/images/apple-touch-icon.png b/app/assets/images/apple-touch-icon.png index b9ebb51ff..97c6d0eff 100644 Binary files a/app/assets/images/apple-touch-icon.png and b/app/assets/images/apple-touch-icon.png differ diff --git a/app/assets/images/favicon-16x16.png b/app/assets/images/favicon-16x16.png index d29295064..0660e0a75 100644 Binary files a/app/assets/images/favicon-16x16.png and b/app/assets/images/favicon-16x16.png differ diff --git a/app/assets/images/favicon-32x32.png b/app/assets/images/favicon-32x32.png index deb773a13..5d7d55940 100644 Binary files a/app/assets/images/favicon-32x32.png and b/app/assets/images/favicon-32x32.png differ diff --git a/app/assets/images/favicon.ico b/app/assets/images/favicon.ico index 457e971cd..de59f534f 100644 Binary files a/app/assets/images/favicon.ico and b/app/assets/images/favicon.ico differ diff --git a/app/assets/images/mstile-150x150.png b/app/assets/images/mstile-150x150.png new file mode 100644 index 000000000..c9f44c8b0 Binary files /dev/null and b/app/assets/images/mstile-150x150.png differ diff --git a/app/assets/images/notify-bell.svg b/app/assets/images/notify-bell.svg new file mode 100644 index 000000000..3b6a267ae --- /dev/null +++ b/app/assets/images/notify-bell.svg @@ -0,0 +1,7 @@ + + + + + + + diff --git a/app/assets/images/notify-dark-favicon.png b/app/assets/images/notify-dark-favicon.png new file mode 100644 index 000000000..2dd4a2603 Binary files /dev/null and b/app/assets/images/notify-dark-favicon.png differ diff --git a/app/assets/images/notify-logo-dark.svg b/app/assets/images/notify-logo-dark.svg new file mode 100644 index 000000000..798ce99d9 --- /dev/null +++ b/app/assets/images/notify-logo-dark.svg @@ -0,0 +1,17 @@ + + + + + + + + + + + + + + + + + diff --git a/app/assets/images/notify-logo.png b/app/assets/images/notify-logo.png new file mode 100644 index 000000000..326d959b6 Binary files /dev/null and b/app/assets/images/notify-logo.png differ diff --git a/app/assets/images/notify-logo.svg b/app/assets/images/notify-logo.svg new file mode 100644 index 000000000..3afb2dd92 --- /dev/null +++ b/app/assets/images/notify-logo.svg @@ -0,0 +1,17 @@ + + + + + + + + + + + + + + + + + diff --git a/app/assets/images/notify-og-image.png b/app/assets/images/notify-og-image.png new file mode 100644 index 000000000..9ca227562 Binary files /dev/null and b/app/assets/images/notify-og-image.png differ diff --git a/app/assets/images/safari-pinned-tab.svg b/app/assets/images/safari-pinned-tab.svg new file mode 100644 index 000000000..580be22c2 --- /dev/null +++ b/app/assets/images/safari-pinned-tab.svg @@ -0,0 +1,24 @@ + + + + +Created by potrace 1.14, written by Peter Selinger 2001-2017 + + + + + + + diff --git a/app/assets/images/site.webmanifest b/app/assets/images/site.webmanifest index 45dc8a206..de65106f4 100644 --- a/app/assets/images/site.webmanifest +++ b/app/assets/images/site.webmanifest @@ -1 +1,19 @@ -{"name":"","short_name":"","icons":[{"src":"/android-chrome-192x192.png","sizes":"192x192","type":"image/png"},{"src":"/android-chrome-512x512.png","sizes":"512x512","type":"image/png"}],"theme_color":"#ffffff","background_color":"#ffffff","display":"standalone"} \ No newline at end of file +{ + "name": "", + "short_name": "", + "icons": [ + { + "src": "/android-chrome-192x192.png", + "sizes": "192x192", + "type": "image/png" + }, + { + "src": "/android-chrome-256x256.png", + "sizes": "256x256", + "type": "image/png" + } + ], + "theme_color": "#ffffff", + "background_color": "#ffffff", + "display": "standalone" +} diff --git a/app/assets/javascripts/loginAlert.js b/app/assets/javascripts/loginAlert.js new file mode 100644 index 000000000..e6343c195 --- /dev/null +++ b/app/assets/javascripts/loginAlert.js @@ -0,0 +1,41 @@ +(function (window) { + +// Set the target date (10 days before March 15th, 2024) + const targetDate = new Date("April 16, 2024 00:00:00").getTime(); + +// Set a const for the container to write a conditional statement and only run if it exists + const countdownContainer = document.getElementById("countdown-container"); + + // Function to update the countdown display + function updateCountdown() { + + if (countdownContainer) { + const now = new Date().getTime(); + const difference = targetDate - now; + + // Time calculations for days only + const days = Math.floor(difference / (1000 * 60 * 60 * 24)); + + // Visibility logic + if (days < 0 || days > 10) { + // Hide if more than 10 days away OR if already past the date + countdownContainer.style.display = "none"; + } else { + // Show if 10 days or less remaining + countdownContainer.style.display = "block"; + document.getElementById("countdown").innerHTML = days + " days "; + } + } + + } + + // Expose the updateCountdown function to the outside world + window.updateCountdown = updateCountdown; + + // Initial display update + updateCountdown(); + + // Update the countdown every second (inside the IIFE) + setInterval(updateCountdown, 1000); + +})(window); diff --git a/app/assets/sass/uswds/_uswds-theme-custom-styles.scss b/app/assets/sass/uswds/_uswds-theme-custom-styles.scss index 55f17a795..54bcd55c8 100644 --- a/app/assets/sass/uswds/_uswds-theme-custom-styles.scss +++ b/app/assets/sass/uswds/_uswds-theme-custom-styles.scss @@ -22,26 +22,35 @@ i.e. @use "uswds-core" as *; +iframe:focus, [href]:focus, [tabindex]:focus, [contentEditable=true]:focus { + outline: units(1px) dotted color('blue-40v'); + outline: units(1px) auto color('blue-40v'); + outline-offset: 0.3rem; +} + .usa-header--extended { .usa-logo { font-family: family("sans"); - margin: units(4) 0; + margin: units(3) 0; @include at-media-max('desktop') { margin: units(4) 0 units(4) units(2); } - img { - @include at-media($theme-header-min-width) { - width: 80px; - height: 70px; + a { + display: flex; + img { + height: 35px; + @include at-media('desktop') { + height: 60px; + } } } } .usa-nav__secondary { .usa-nav__link { - padding: 0; - &.usa-current { - text-decoration: underline; - } + padding: 0; + &.usa-current { + text-decoration: underline; + } } @include at-media-max('desktop') { padding: 0 units(2); @@ -62,18 +71,23 @@ i.e. .usa-nav__primary { &> .usa-nav__primary-item > a { - font-size: size("body", 4); + font-size: size("body", 5); + font-weight: 400; + cursor: pointer; } - // &> .usa-nav__primary-item:last-child { - // margin-left: auto; - // @include u-margin-right(-4); - // } } h1 { font-weight: bold !important; } +.usa-section--dark h1 { + color: color('blue-30v'); + @include at-media-max('desktop') { + font-size: size("body", 12); + } +} + p, .list li { font-family: family("sans"); @@ -568,3 +582,9 @@ details form { .edit-textbox-error-mt { margin-top: 1.5rem; } + +// Login page + +#countdown-container { + display: none; // Hide the countdown timer +} diff --git a/app/config.py b/app/config.py index 58623f426..ba89ce6bf 100644 --- a/app/config.py +++ b/app/config.py @@ -36,6 +36,7 @@ class Config(object): NR_BROWSER_KEY = getenv("NR_BROWSER_KEY") settings = newrelic.agent.global_settings() NR_MONITOR_ON = settings and settings.monitor_mode + COMMIT_HASH = getenv("COMMIT_HASH", "--------")[0:7] TEMPLATE_PREVIEW_API_HOST = getenv( "TEMPLATE_PREVIEW_API_HOST", "http://localhost:9999" diff --git a/app/main/views/send.py b/app/main/views/send.py index 560c5cb3a..8853b7fc3 100644 --- a/app/main/views/send.py +++ b/app/main/views/send.py @@ -1,4 +1,3 @@ -import itertools import time import uuid from string import ascii_uppercase @@ -517,19 +516,29 @@ def _check_messages(service_id, template_id, upload_id, preview_row): current_service, show_recipient=False, ) + + allow_list = [] + if current_service.trial_mode: + # Adding the simulated numbers to allow list + # so they can be sent in trial mode + for user in Users(service_id): + allow_list.extend([user.name, user.mobile_number, user.email_address]) + # Failed sms number + allow_list.extend( + ["simulated user (fail)", "+14254147167", "simulated@simulated.gov"] + ) + # Success sms number + allow_list.extend( + ["simulated user (success)", "+14254147755", "simulatedtwo@simulated.gov"] + ) + else: + allow_list = None recipients = RecipientCSV( contents, template=template or simplifed_template, max_initial_rows_shown=50, max_errors_shown=50, - guestlist=( - itertools.chain.from_iterable( - [user.name, user.mobile_number, user.email_address] - for user in Users(service_id) - ) - if current_service.trial_mode - else None - ), + guestlist=allow_list, remaining_messages=remaining_messages, allow_international_sms=current_service.has_permission("international_sms"), ) diff --git a/app/main/views/sign_in.py b/app/main/views/sign_in.py index d39cb89af..5c5cf8a45 100644 --- a/app/main/views/sign_in.py +++ b/app/main/views/sign_in.py @@ -196,7 +196,7 @@ def sign_in(): form=form, again=bool(redirect_url), other_device=other_device, - login_gov_enabled=bool(notify_env in ["development", "staging", "demo"]), + login_gov_enabled=True, password_reset_url=password_reset_url, initial_signin_url=initial_signin_url, ) diff --git a/app/templates/admin_template.html b/app/templates/admin_template.html index 6b33fed05..cfa92a7e0 100644 --- a/app/templates/admin_template.html +++ b/app/templates/admin_template.html @@ -21,7 +21,7 @@ {% endblock %} {% block meta %} - + {% endblock %} {% endblock %} @@ -175,11 +175,13 @@ {% endblock %} {% block footer %} - + {% if current_service and current_service.research_mode %} {% set meta_suffix = 'Built by the Technology Transformation Servicesresearch mode' %} {% else %} - {% set meta_suffix = 'Built by the Technology Transformation Services' %} + {% set commit_hash = ", Latest version: " + config['COMMIT_HASH'] %} + {% set long_link = 'Technology Transformation Services' %} + {% set meta_suffix = "Built by the " + long_link + commit_hash %} {% endif %} {{ usaFooter({ @@ -240,7 +242,7 @@ { "href": url_for('main.support'), "text": "Contact us" - }, + } ] }, ], @@ -249,7 +251,7 @@ "html": meta_suffix } }) }} - + {% if current_user.is_authenticated %} {% block sessionUserWarning %} diff --git a/app/templates/components/components/header/template.njk b/app/templates/components/components/header/template.njk index a4cd0d9e2..c0620d502 100644 --- a/app/templates/components/components/header/template.njk +++ b/app/templates/components/components/header/template.njk @@ -47,14 +47,13 @@