diff --git a/.eslintrc.js b/.eslintrc.js index ac4546567833..b5b4add538f6 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -24,7 +24,7 @@ const restrictedImportPatterns = [ ]; module.exports = { - extends: ['expensify', 'plugin:storybook/recommended', 'plugin:react-hooks/recommended', 'prettier', 'plugin:react-native-a11y/basic'], + extends: ['expensify', 'plugin:storybook/recommended', 'plugin:react-hooks/recommended', 'plugin:react-native-a11y/basic', 'prettier'], plugins: ['react-hooks', 'react-native-a11y'], parser: 'babel-eslint', ignorePatterns: ['!.*', 'src/vendor', '.github/actions/**/index.js', 'desktop/dist/*.js', 'dist/*.js', 'node_modules/.bin/**', 'node_modules/.cache/**', '.git/**'], @@ -75,6 +75,7 @@ module.exports = { patterns: restrictedImportPatterns, }, ], + curly: 'error', }, }, { @@ -161,6 +162,7 @@ module.exports = { patterns: restrictedImportPatterns, }, ], + curly: 'error', }, }, { diff --git a/.github/ISSUE_TEMPLATE/Accessibility.md b/.github/ISSUE_TEMPLATE/Accessibility.md index 36a64aa25b43..1323e2c17e78 100644 --- a/.github/ISSUE_TEMPLATE/Accessibility.md +++ b/.github/ISSUE_TEMPLATE/Accessibility.md @@ -34,7 +34,7 @@ What can we do to fix the issue? -Which of our officially supported platforms is this issue occurring on? +Which of our officially supported platforms is this issue occurring on? Please only tick the box if you have provided a screen-recording in the thread for each platform: - [ ] Android / native - [ ] Android / Chrome - [ ] iOS / native diff --git a/.github/scripts/createDocsRoutes.js b/.github/scripts/createDocsRoutes.js index 0fc9aa33ff27..6604a9d207fa 100644 --- a/.github/scripts/createDocsRoutes.js +++ b/.github/scripts/createDocsRoutes.js @@ -2,17 +2,21 @@ const yaml = require('js-yaml'); const fs = require('fs'); const _ = require('underscore'); -const warn = 'Number of hubs in _routes.yml does not match number of hubs in docs/articles. Please update _routes.yml with hub info.'; +const warnMessage = (platform) => `Number of hubs in _routes.yml does not match number of hubs in docs/${platform}/articles. Please update _routes.yml with hub info.`; const disclaimer = '# This file is auto-generated. Do not edit it directly. Use npm run createDocsRoutes instead.\n'; const docsDir = `${process.cwd()}/docs`; const routes = yaml.load(fs.readFileSync(`${docsDir}/_data/_routes.yml`, 'utf8')); +const platformNames = { + expensifyClassic: 'expensify-classic', + newExpensify: 'new-expensify', +}; /** * @param {String} str - The string to convert to title case * @returns {String} */ function toTitleCase(str) { - return str.replace(/\w\S*/g, (txt) => txt.charAt(0).toUpperCase() + txt.substr(1).toLowerCase()); + return str.replace(/\w\S*/g, (txt) => txt.charAt(0).toUpperCase() + txt.substr(1)); } /** @@ -28,7 +32,7 @@ function getArticleObj(filename) { } /** - * If the articlea / sections exist in the hub, then push the entry to the array. + * If the article / sections exist in the hub, then push the entry to the array. * Otherwise, create the array and push the entry to it. * @param {*} hubs - The hubs array * @param {*} hub - The hub we are iterating @@ -44,20 +48,20 @@ function pushOrCreateEntry(hubs, hub, key, entry) { } } -function run() { - const hubs = fs.readdirSync(`${docsDir}/articles`); - if (hubs.length !== routes.hubs.length) { - // If new hubs have been added without metadata addition to _routes.yml - console.error(warn); - process.exit(1); - } +/** + * Add articles and sections to hubs + * @param {Array} hubs - The hubs inside docs/articles/ for a platform + * @param {String} platformName - Expensify Classic or New Expensify + * @param {Array} routeHubs - The hubs insude docs/data/_routes.yml for a platform + */ +function createHubsWithArticles(hubs, platformName, routeHubs) { _.each(hubs, (hub) => { // Iterate through each directory in articles - fs.readdirSync(`${docsDir}/articles/${hub}`).forEach((fileOrFolder) => { + fs.readdirSync(`${docsDir}/articles/${platformName}/${hub}`).forEach((fileOrFolder) => { // If the directory content is a markdown file, then it is an article if (fileOrFolder.endsWith('.md')) { const articleObj = getArticleObj(fileOrFolder); - pushOrCreateEntry(routes.hubs, hub, 'articles', articleObj); + pushOrCreateEntry(routeHubs, hub, 'articles', articleObj); return; } @@ -66,17 +70,38 @@ function run() { const articles = []; // Each subfolder will be a section containing articles - fs.readdirSync(`${docsDir}/articles/${hub}/${section}`).forEach((subArticle) => { + fs.readdirSync(`${docsDir}/articles/${platformName}/${hub}/${section}`).forEach((subArticle) => { articles.push(getArticleObj(subArticle)); }); - pushOrCreateEntry(routes.hubs, hub, 'sections', { + pushOrCreateEntry(routeHubs, hub, 'sections', { href: section, title: toTitleCase(section.replaceAll('-', ' ')), articles, }); }); }); +} + +function run() { + const expensifyClassicArticleHubs = fs.readdirSync(`${docsDir}/articles/${platformNames.expensifyClassic}`); + const newExpensifyArticleHubs = fs.readdirSync(`${docsDir}/articles/${platformNames.newExpensify}`); + + const expensifyClassicRoute = _.find(routes.platforms, (platform) => platform.href === platformNames.expensifyClassic); + const newExpensifyRoute = _.find(routes.platforms, (platform) => platform.href === platformNames.newExpensify); + + if (expensifyClassicArticleHubs.length !== expensifyClassicRoute.hubs.length) { + console.error(warnMessage(platformNames.expensifyClassic)); + process.exit(1); + } + + if (newExpensifyArticleHubs.length !== newExpensifyRoute.hubs.length) { + console.error(warnMessage(platformNames.newExpensify)); + process.exit(1); + } + + createHubsWithArticles(expensifyClassicArticleHubs, platformNames.expensifyClassic, expensifyClassicRoute.hubs); + createHubsWithArticles(newExpensifyArticleHubs, platformNames.newExpensify, newExpensifyRoute.hubs); // Convert the object to YAML and write it to the file let yamlString = yaml.dump(routes); diff --git a/.github/scripts/findUnusedKeys.sh b/.github/scripts/findUnusedKeys.sh new file mode 100755 index 000000000000..77c3ea25326b --- /dev/null +++ b/.github/scripts/findUnusedKeys.sh @@ -0,0 +1,375 @@ +#!/bin/bash + +# Configurations +declare LIB_PATH +LIB_PATH="$(cd "$(dirname "${BASH_SOURCE[0]}")" && cd ../../ && pwd)" + +readonly SRC_DIR="${LIB_PATH}/src" +readonly STYLES_DIR="${LIB_PATH}/src/styles" +readonly STYLES_FILE="${LIB_PATH}/src/styles/styles.js" +readonly UTILITIES_STYLES_FILE="${LIB_PATH}/src/styles/utilities" +readonly STYLES_KEYS_FILE="${LIB_PATH}/scripts/style_keys_list_temp.txt" +readonly UTILITY_STYLES_KEYS_FILE="${LIB_PATH}/scripts/utility_keys_list_temp.txt" +readonly REMOVAL_KEYS_FILE="${LIB_PATH}/scripts/removal_keys_list_temp.txt" +readonly AMOUNT_LINES_TO_SHOW=3 + +readonly FILE_EXTENSIONS=('-name' '*.js' '-o' '-name' '*.jsx' '-o' '-name' '*.ts' '-o' '-name' '*.tsx') + +source scripts/shellUtils.sh + +# trap ctrl-c and call ctrl_c() +trap ctrl_c INT + +delete_temp_files() { + find "${LIB_PATH}/scripts" -name "*keys_list_temp*" -type f -exec rm -f {} \; +} + +# shellcheck disable=SC2317 # Don't warn about unreachable commands in this function +ctrl_c() { + delete_temp_files + exit 1 +} + +count_lines() { + local file=$1 + if [[ -e "$file" ]]; then + wc -l < "$file" + else + echo "File not found: $file" + fi +} + +# Read the style file with unused keys +show_unused_style_keywords() { + while IFS=: read -r key file line_number; do + title "File: $file:$line_number" + + # Get lines before and after the error line + local lines_before=$((line_number - AMOUNT_LINES_TO_SHOW)) + local lines_after=$((line_number + AMOUNT_LINES_TO_SHOW)) + + # Read the lines into an array + local lines=() + while IFS= read -r line; do + lines+=("$line") + done < "$file" + + # Loop through the lines + for ((i = lines_before; i <= lines_after; i++)); do + local line="${lines[i]}" + # Print context of the error line + echo "$line" + done + error "Unused key: $key" + echo "--------------------------------" + done < "$STYLES_KEYS_FILE" +} + +# Function to remove a keyword from the temp file +remove_keyword() { + local keyword="$1" + if grep -q "$keyword" "$STYLES_KEYS_FILE"; then + grep -v "$keyword" "$STYLES_KEYS_FILE" > "$REMOVAL_KEYS_FILE" + mv "$REMOVAL_KEYS_FILE" "$STYLES_KEYS_FILE" + + return 0 # Keyword was removed + else + return 1 # Keyword was not found + fi +} + +lookfor_unused_keywords() { + # Loop through all files in the src folder + while read -r file; do + + # Search for keywords starting with "styles" + while IFS= read -r keyword; do + + # Remove any [ ] characters from the keyword + local clean_keyword="${keyword//[\[\]]/}" + # skip styles. keyword that might be used in comments + if [[ "$clean_keyword" == "styles." ]]; then + continue + fi + + if ! remove_keyword "$clean_keyword" ; then + # In case of a leaf of the styles object is being used, it means the parent objects is being used + # we need to mark it as used. + if [[ "$clean_keyword" =~ ^styles\.[a-zA-Z0-9_-]+\.[a-zA-Z0-9_-]+$ ]]; then + # Keyword has more than two words, remove words after the second word + local keyword_prefix="${clean_keyword%.*}" + remove_keyword "$keyword_prefix" + fi + fi + done < <(grep -E -o '\bstyles\.[a-zA-Z0-9_.]*' "$file" | grep -v '\/\/' | grep -vE '\/\*.*\*\/') + done < <(find "${SRC_DIR}" -type f \( "${FILE_EXTENSIONS[@]}" \)) +} + + +# Function to find and store keys from a file +find_styles_object_and_store_keys() { + local file="$1" + local base_name="${2:-styles}" # Set styles as default + local line_number=0 + local inside_arrow_function=false + + while IFS= read -r line; do + ((line_number++)) + + # Check if we are inside an arrow function and we find a closing curly brace + if [[ "$inside_arrow_function" == true ]]; then + if [[ "$line" =~ ^[[:space:]]*\}\) ]]; then + inside_arrow_function=false + fi + continue + fi + + # Check if we are inside an arrow function + if [[ "$line" =~ ^[[:space:]]*([a-zA-Z0-9_-])+:[[:space:]]*\(.*\)[[:space:]]*'=>'[[:space:]]*\(\{ || "$line" =~ ^[[:space:]]*(const|let|var)[[:space:]]+([a-zA-Z0-9_-]+)[[:space:]]*=[[:space:]]*\(.*\)[[:space:]]*'=>' ]]; then + inside_arrow_function=true + continue + fi + + # Skip lines that are not key-related + if [[ ! "$line" =~ ^[[:space:]]*(const|let|var)[[:space:]]+([a-zA-Z0-9_-]+)[[:space:]]*=[[:space:]]*\{|^[[:space:]]*([a-zA-Z0-9_-]+\.)?[a-zA-Z0-9_-]+:[[:space:]]*\{|^[[:space:]]*\} ]]; then + continue + fi + + if [[ "$line" =~ ^[[:space:]]*(const|let|var)[[:space:]]+([a-zA-Z0-9_-]+)[[:space:]]*=[[:space:]]*\{ ]]; then + key="${BASH_REMATCH[2]%%:*{*)}" + echo "styles.${key}|...${key}|${base_name}.${key}:${file}:${line_number}" >> "$STYLES_KEYS_FILE" + fi + done < "$file" +} + +find_styles_functions_and_store_keys() { + local file="$1" + local line_number=0 + local inside_object=false + local inside_arrow_function=false + local key="" + + while IFS= read -r line; do + ((line_number++)) + + # Skip lines that are not key-related + if [[ "${line}" == *styles* ]]; then + continue + fi + + # Check if we are inside an arrow function and we find a closing curly brace + if [[ "$inside_arrow_function" == true ]]; then + if [[ "$line" =~ ^[[:space:]]*\}\) ]]; then + inside_arrow_function=false + fi + continue + fi + + # Check if we are inside an arrow function + if [[ "${line}" =~ ^[[:space:]]*([a-zA-Z0-9_-])+:[[:space:]]*\(.*\)[[:space:]]*'=>'[[:space:]]*\( ]]; then + inside_arrow_function=true + key="${line%%:*}" + key="${key// /}" # Trim spaces + echo "styles.${key}|...${key}:${file}:${line_number}" >> "$STYLES_KEYS_FILE" + continue + fi + + if [[ "$line" =~ ^[[:space:]]*(const|let|var)[[:space:]]+([a-zA-Z0-9_-]+)[[:space:]]*=[[:space:]]*\(.*\)[[:space:]]*'=>' ]]; then + inside_arrow_function=true + key="${BASH_REMATCH[2]}" + key="${key// /}" # Trim spaces + echo "styles.${key}|...${key}:${file}:${line_number}" >> "$STYLES_KEYS_FILE" + continue + fi + + done < "$file" +} + +find_theme_style_and_store_keys() { + local file="$1" + local start_line_number="$2" + local base_name="${3:-styles}" # Set styles as default + local parent_keys=() + local root_key="" + local line_number=0 + local inside_arrow_function=false + + while IFS= read -r line; do + ((line_number++)) + + if [ ! "$line_number" -ge "$start_line_number" ]; then + continue + fi + + # Check if we are inside an arrow function and we find a closing curly brace + if [[ "$inside_arrow_function" == true ]]; then + if [[ "$line" =~ ^[[:space:]]*\}\) ]]; then + inside_arrow_function=false + fi + continue + fi + + # Check if we are inside an arrow function + if [[ "$line" =~ ^[[:space:]]*([a-zA-Z0-9_-])+:[[:space:]]*\(.*\)[[:space:]]*'=>'[[:space:]]*\(\{ || "$line" =~ ^[[:space:]]*(const|let|var)[[:space:]]+([a-zA-Z0-9_-]+)[[:space:]]*=[[:space:]]*\(.*\)[[:space:]]*'=>' ]]; then + inside_arrow_function=true + continue + fi + + # Skip lines that are not key-related + if [[ ! "$line" =~ ^[[:space:]]*(const|let|var)[[:space:]]+([a-zA-Z0-9_-]+)[[:space:]]*=[[:space:]]*\{|^[[:space:]]*([a-zA-Z0-9_-]+\.)?[a-zA-Z0-9_-]+:[[:space:]]*\{|^[[:space:]]*\} ]]; then + + continue + fi + + if [[ "$line" =~ ^[[:space:]]*([a-zA-Z0-9_-]+\.)?[a-zA-Z0-9_-]+:[[:space:]]*\{|^[[:space:]]*([a-zA-Z0-9_-])+:[[:space:]]*\(.*\)[[:space:]]*'=>'[[:space:]]*\(\{ ]]; then + # Removing all the extra lines after the ":" + local key="${line%%:*}" + key="${key// /}" # Trim spaces + + if [[ ${#parent_keys[@]} -gt 0 ]]; then + local parent_key_trimmed="${parent_keys[${#parent_keys[@]}-1]// /}" # Trim spaces + key="$parent_key_trimmed.$key" + elif [[ -n "$root_key" ]]; then + local parent_key_trimmed="${root_key// /}" # Trim spaces + key="$parent_key_trimmed.$key" + fi + + echo "styles.${key}|...${key}|${base_name}.${key}:${file}:${line_number}" >> "$STYLES_KEYS_FILE" + parent_keys+=("$key") + elif [[ "$line" =~ ^[[:space:]]*\} ]]; then + parent_keys=("${parent_keys[@]:0:${#parent_keys[@]}-1}") + fi + done < "$file" +} + +# Given that all the styles are inside of a function, we need to find the function and then look for the styles +collect_theme_keys_from_styles() { + local file="$1" + local line_number=0 + local inside_styles=false + + while IFS= read -r line; do + ((line_number++)) + + if [[ "$inside_styles" == false ]]; then + if [[ "$line" =~ ^[[:space:]]*(const|let|var)[[:space:]]+([a-zA-Z0-9_-]+)[[:space:]]*=[[:space:]]*\(.*\)[[:space:]]*'=>' ]]; then + key="${BASH_REMATCH[2]}" + key="${key// /}" # Trim spaces + if [[ "$key" == "styles"* ]]; then + inside_styles=true + # Need to start within the style function + ((line_number++)) + find_theme_style_and_store_keys "$STYLES_FILE" "$line_number" + fi + continue + fi + fi + done < "$file" +} + +lookfor_unused_spread_keywords() { + local inside_object=false + local key="" + + while IFS= read -r line; do + # Detect the start of an object + if [[ "$line" =~ ^[[:space:]]*([a-zA-Z0-9_-]+\.)?[a-zA-Z0-9_-]+:[[:space:]]*\{ ]]; then + inside_object=true + fi + + # Detect the end of an object + if [[ "$line" =~ ^[[:space:]]*\},?$ ]]; then + inside_object=false + fi + + # If we're inside an object and the line starts with '...', capture the key + if [[ "$inside_object" == true && "$line" =~ ^[[:space:]]*\.\.\.([a-zA-Z0-9_]+)(\(.+\))?,?$ ]]; then + key="${BASH_REMATCH[1]}" + remove_keyword "...${key}" + fi + done < "$STYLES_FILE" +} + +find_utility_styles_store_prefix() { + # Loop through all files in the src folder + while read -r file; do + # Search for keywords starting with "styles" + while IFS= read -r keyword; do + local variable="${keyword##*/}" + local variable_trimmed="${variable// /}" # Trim spaces + + echo "$variable_trimmed" >> "$UTILITY_STYLES_KEYS_FILE" + done < <(grep -E -o './utilities/[a-zA-Z0-9_-]+' "$file" | grep -v '\/\/' | grep -vE '\/\*.*\*\/') + done < <(find "${STYLES_DIR}" -type f \( "${FILE_EXTENSIONS[@]}" \)) + + # Sort and remove duplicates from the temporary file + sort -u -o "${UTILITY_STYLES_KEYS_FILE}" "${UTILITY_STYLES_KEYS_FILE}" +} + +find_utility_usage_as_styles() { + while read -r file; do + local root_key + local parent_dir + + # Get the folder name, given this utility files are index.js + parent_dir=$(dirname "$file") + root_key=$(basename "${parent_dir}") + + if [[ "${root_key}" == "utilities" ]]; then + continue + fi + + find_theme_style_and_store_keys "${file}" 0 "${root_key}" + done < <(find "${UTILITIES_STYLES_FILE}" -type f \( "${FILE_EXTENSIONS[@]}" \)) +} + +lookfor_unused_utilities() { + # Read each utility keyword from the file + while read -r keyword; do + # Creating a copy so later the replacement can reference it + local original_keyword="${keyword}" + + # Iterate through all files in "src/styles" + while read -r file; do + # Find all words that match "$keyword.[a-zA-Z0-9_-]+" + while IFS= read -r match; do + # Replace the utility prefix with "styles" + local variable="${match/#$original_keyword/styles}" + # Call the remove_keyword function with the variable + remove_keyword "${variable}" + remove_keyword "${match}" + done < <(grep -E -o "$original_keyword\.[a-zA-Z0-9_-]+" "$file" | grep -v '\/\/' | grep -vE '\/\*.*\*\/') + done < <(find "${STYLES_DIR}" -type f \( "${FILE_EXTENSIONS[@]}" \)) + done < "$UTILITY_STYLES_KEYS_FILE" +} + +echo "🔍 Looking for styles." +# Find and store the name of the utility files as keys +find_utility_styles_store_prefix +find_utility_usage_as_styles + +# Find and store keys from styles.js +find_styles_object_and_store_keys "$STYLES_FILE" +find_styles_functions_and_store_keys "$STYLES_FILE" +collect_theme_keys_from_styles "$STYLES_FILE" + +echo "🗄️ Now going through the codebase and looking for unused keys." + +# Look for usages of utilities into src/styles +lookfor_unused_utilities +lookfor_unused_spread_keywords +lookfor_unused_keywords + +final_styles_line_count=$(count_lines "$STYLES_KEYS_FILE") + +if [[ $final_styles_line_count -eq 0 ]]; then + # Exit successfully (status code 0) + delete_temp_files + success "Styles are in a good shape" + exit 0 +else + show_unused_style_keywords + delete_temp_files + error "Unused keys: $final_styles_line_count" + exit 1 +fi diff --git a/.github/workflows/lint.yml b/.github/workflows/lint.yml index 5953a4aa89e2..b403a1eb737c 100644 --- a/.github/workflows/lint.yml +++ b/.github/workflows/lint.yml @@ -33,3 +33,7 @@ jobs: echo 'Error: Prettier diff detected! Please run `npm run prettier` and commit the changes.' exit 1 fi + + - name: Run unused style searcher + shell: bash + run: ./.github/scripts/findUnusedKeys.sh diff --git a/.gitignore b/.gitignore index aae9baad529f..d3b4daac04d7 100644 --- a/.gitignore +++ b/.gitignore @@ -107,3 +107,7 @@ tsconfig.tsbuildinfo # Workflow test logs /workflow_tests/logs/ + +# Yalc +.yalc +yalc.lock diff --git a/Cloudflare_CA.crt b/Cloudflare_CA.crt new file mode 100644 index 000000000000..f02f49a951fc Binary files /dev/null and b/Cloudflare_CA.crt differ diff --git a/Gemfile.lock b/Gemfile.lock index 9487e3c45c7a..079b5a5b742b 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -9,7 +9,7 @@ GEM minitest (>= 5.1) tzinfo (~> 2.0) zeitwerk (~> 2.3) - addressable (2.8.3) + addressable (2.8.5) public_suffix (>= 2.0.2, < 6.0) algoliasearch (1.27.5) httpclient (~> 2.8, >= 2.8.3) @@ -19,20 +19,20 @@ GEM artifactory (3.0.15) atomos (0.1.3) aws-eventstream (1.2.0) - aws-partitions (1.646.0) - aws-sdk-core (3.160.0) + aws-partitions (1.824.0) + aws-sdk-core (3.181.1) aws-eventstream (~> 1, >= 1.0.2) - aws-partitions (~> 1, >= 1.525.0) - aws-sigv4 (~> 1.1) + aws-partitions (~> 1, >= 1.651.0) + aws-sigv4 (~> 1.5) jmespath (~> 1, >= 1.6.1) - aws-sdk-kms (1.58.0) - aws-sdk-core (~> 3, >= 3.127.0) + aws-sdk-kms (1.71.0) + aws-sdk-core (~> 3, >= 3.177.0) aws-sigv4 (~> 1.1) - aws-sdk-s3 (1.114.0) - aws-sdk-core (~> 3, >= 3.127.0) + aws-sdk-s3 (1.134.0) + aws-sdk-core (~> 3, >= 3.181.0) aws-sdk-kms (~> 1) - aws-sigv4 (~> 1.4) - aws-sigv4 (1.5.2) + aws-sigv4 (~> 1.6) + aws-sigv4 (1.6.0) aws-eventstream (~> 1, >= 1.0.2) babosa (1.0.4) claide (1.1.0) @@ -79,7 +79,7 @@ GEM highline (~> 2.0.0) concurrent-ruby (1.2.2) declarative (0.0.20) - digest-crc (0.6.4) + digest-crc (0.6.5) rake (>= 12.0.0, < 14.0.0) domain_name (0.5.20190701) unf (>= 0.0.5, < 1.0.0) @@ -88,8 +88,8 @@ GEM escape (0.0.4) ethon (0.16.0) ffi (>= 1.15.0) - excon (0.93.0) - faraday (1.10.2) + excon (0.103.0) + faraday (1.10.3) faraday-em_http (~> 1.0) faraday-em_synchrony (~> 1.0) faraday-excon (~> 1.1) @@ -117,8 +117,8 @@ GEM faraday-retry (1.0.3) faraday_middleware (1.2.0) faraday (~> 1.0) - fastimage (2.2.6) - fastlane (2.210.1) + fastimage (2.2.7) + fastlane (2.215.1) CFPropertyList (>= 2.3, < 4.0.0) addressable (>= 2.8, < 3.0.0) artifactory (~> 3.0) @@ -139,10 +139,11 @@ GEM google-apis-playcustomapp_v1 (~> 0.1) google-cloud-storage (~> 1.31) highline (~> 2.0) + http-cookie (~> 1.0.5) json (< 3.0.0) jwt (>= 2.1.0, < 3) mini_magick (>= 4.9.4, < 5.0.0) - multipart-post (~> 2.0.0) + multipart-post (>= 2.0.0, < 3.0.0) naturally (~> 2.2) optparse (~> 0.1.1) plist (>= 3.1.0, < 4.0.0) @@ -150,7 +151,7 @@ GEM security (= 0.1.3) simctl (~> 1.6.3) terminal-notifier (>= 2.0.0, < 3.0.0) - terminal-table (>= 1.4.5, < 2.0.0) + terminal-table (~> 3) tty-screen (>= 0.6.3, < 1.0.0) tty-spinner (>= 0.8.0, < 1.0.0) word_wrap (~> 1.0.0) @@ -165,9 +166,9 @@ GEM fourflusher (2.3.1) fuzzy_match (2.0.4) gh_inspector (1.1.3) - google-apis-androidpublisher_v3 (0.29.0) - google-apis-core (>= 0.9.0, < 2.a) - google-apis-core (0.9.0) + google-apis-androidpublisher_v3 (0.49.0) + google-apis-core (>= 0.11.0, < 2.a) + google-apis-core (0.11.1) addressable (~> 2.5, >= 2.5.1) googleauth (>= 0.16.2, < 2.a) httpclient (>= 2.8.1, < 3.a) @@ -176,10 +177,10 @@ GEM retriable (>= 2.0, < 4.a) rexml webrick - google-apis-iamcredentials_v1 (0.15.0) - google-apis-core (>= 0.9.0, < 2.a) - google-apis-playcustomapp_v1 (0.11.0) - google-apis-core (>= 0.9.0, < 2.a) + google-apis-iamcredentials_v1 (0.17.0) + google-apis-core (>= 0.11.0, < 2.a) + google-apis-playcustomapp_v1 (0.13.0) + google-apis-core (>= 0.11.0, < 2.a) google-apis-storage_v1 (0.19.0) google-apis-core (>= 0.9.0, < 2.a) google-cloud-core (1.6.0) @@ -187,8 +188,8 @@ GEM google-cloud-errors (~> 1.0) google-cloud-env (1.6.0) faraday (>= 0.17.3, < 3.0) - google-cloud-errors (1.3.0) - google-cloud-storage (1.43.0) + google-cloud-errors (1.3.1) + google-cloud-storage (1.44.0) addressable (~> 2.8) digest-crc (~> 0.4) google-apis-iamcredentials_v1 (~> 0.1) @@ -196,10 +197,9 @@ GEM google-cloud-core (~> 1.6) googleauth (>= 0.16.2, < 2.a) mini_mime (~> 1.0) - googleauth (1.2.0) + googleauth (1.8.0) faraday (>= 0.17.3, < 3.a) jwt (>= 1.4, < 3.0) - memoist (~> 0.16) multi_json (~> 1.11) os (>= 0.9, < 2.0) signet (>= 0.16, < 2.a) @@ -209,26 +209,25 @@ GEM httpclient (2.8.3) i18n (1.13.0) concurrent-ruby (~> 1.0) - jmespath (1.6.1) + jmespath (1.6.2) json (2.6.3) - jwt (2.5.0) - memoist (0.16.2) + jwt (2.7.1) mime-types (3.4.1) mime-types-data (~> 3.2015) mime-types-data (3.2023.0218.1) - mini_magick (4.11.0) - mini_mime (1.1.2) + mini_magick (4.12.0) + mini_mime (1.1.5) minitest (5.18.0) molinillo (0.8.0) multi_json (1.15.0) - multipart-post (2.0.0) + multipart-post (2.3.0) nanaimo (0.3.0) nap (1.1.0) naturally (2.2.1) netrc (0.11.0) optparse (0.1.1) os (1.1.4) - plist (3.6.0) + plist (3.7.0) public_suffix (4.0.7) rake (13.0.6) representable (3.2.0) @@ -236,23 +235,23 @@ GEM trailblazer-option (>= 0.1.1, < 0.2.0) uber (< 0.2.0) retriable (3.1.2) - rexml (3.2.5) + rexml (3.2.6) rouge (2.0.7) ruby-macho (2.5.1) ruby2_keywords (0.0.5) rubyzip (2.3.2) security (0.1.3) - signet (0.17.0) + signet (0.18.0) addressable (~> 2.8) faraday (>= 0.17.5, < 3.a) jwt (>= 1.5, < 3.0) multi_json (~> 1.10) - simctl (1.6.8) + simctl (1.6.10) CFPropertyList naturally terminal-notifier (2.0.0) - terminal-table (1.8.0) - unicode-display_width (~> 1.1, >= 1.1.1) + terminal-table (3.0.2) + unicode-display_width (>= 1.1.1, < 3) trailblazer-option (0.1.2) tty-cursor (0.7.1) tty-screen (0.8.1) @@ -266,8 +265,8 @@ GEM unf (0.1.4) unf_ext unf_ext (0.0.8.2) - unicode-display_width (1.8.0) - webrick (1.7.0) + unicode-display_width (2.4.2) + webrick (1.8.1) word_wrap (1.0.0) xcodeproj (1.22.0) CFPropertyList (>= 2.3.3, < 4.0) diff --git a/android/app/build.gradle b/android/app/build.gradle index f957ea7c5854..bcac489f6828 100644 --- a/android/app/build.gradle +++ b/android/app/build.gradle @@ -90,8 +90,8 @@ android { minSdkVersion rootProject.ext.minSdkVersion targetSdkVersion rootProject.ext.targetSdkVersion multiDexEnabled rootProject.ext.multiDexEnabled - versionCode 1001037105 - versionName "1.3.71-5" + versionCode 1001037402 + versionName "1.3.74-2" } flavorDimensions "default" diff --git a/android/app/src/main/java/com/expensify/chat/customairshipextender/CustomNotificationProvider.java b/android/app/src/main/java/com/expensify/chat/customairshipextender/CustomNotificationProvider.java index 0ba77f809b19..c60476ad3f0a 100644 --- a/android/app/src/main/java/com/expensify/chat/customairshipextender/CustomNotificationProvider.java +++ b/android/app/src/main/java/com/expensify/chat/customairshipextender/CustomNotificationProvider.java @@ -106,7 +106,8 @@ protected NotificationCompat.Builder onExtendBuilder(@NonNull Context context, @ if (payload.containsKey(ONYX_DATA_KEY)) { Objects.requireNonNull(payload.get(ONYX_DATA_KEY)).isNull(); Log.d(TAG, "payload contains onxyData"); - applyMessageStyle(context, builder, payload, arguments.getNotificationId()); + String alert = message.getExtra(PushMessage.EXTRA_ALERT); + applyMessageStyle(context, builder, payload, arguments.getNotificationId(), alert); } } catch (Exception e) { Log.e(TAG, "Failed to parse conversation, falling back to default notification style. SendID=" + message.getSendId(), e); @@ -163,7 +164,7 @@ public Bitmap getCroppedBitmap(Bitmap bitmap) { * @param payload Notification payload, which contains all the data we need to build the notifications. * @param notificationID Current notification ID */ - private void applyMessageStyle(@NonNull Context context, NotificationCompat.Builder builder, JsonMap payload, int notificationID) { + private void applyMessageStyle(@NonNull Context context, NotificationCompat.Builder builder, JsonMap payload, int notificationID, String alert) { long reportID = payload.get("reportID").getLong(-1); if (reportID == -1) { return; @@ -181,7 +182,9 @@ private void applyMessageStyle(@NonNull Context context, NotificationCompat.Buil String name = messageData.get("person").getList().get(0).getMap().get("text").getString(); String avatar = messageData.get("avatar").getString(); String accountID = Integer.toString(messageData.get("actorAccountID").getInt(-1)); - String message = messageData.get("message").getList().get(0).getMap().get("text").getString(); + + // Use the formatted alert message from the backend. Otherwise fallback on the message in the Onyx data. + String message = alert != null ? alert : messageData.get("message").getList().get(0).getMap().get("text").getString(); String conversationName = payload.get("roomName") == null ? "" : payload.get("roomName").getString(""); // Retrieve or create the Person object who sent the latest report comment diff --git a/assets/images/expensify-card.svg b/assets/images/expensify-card.svg new file mode 100644 index 000000000000..f95e3ed20288 --- /dev/null +++ b/assets/images/expensify-card.svg @@ -0,0 +1,69 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/contributingGuides/ACCESSIBILITY.md b/contributingGuides/ACCESSIBILITY.md new file mode 100644 index 000000000000..b94cbf3087c8 --- /dev/null +++ b/contributingGuides/ACCESSIBILITY.md @@ -0,0 +1,47 @@ +# Accessibility of pressable components + +### Base Components + +- **GenericPressable**: A basic pressable component with generic functionality. It should generally only be used to creating a new, custom pressable components. Avoid using it directly. + +- **PressableWithFeedback**: A pressable component that provides standarised visual and haptic feedback upon pressing. + +- **PressableWithoutFeedback**: A pressable component without any visual or haptic feedback. + +- **PressableWithoutFocus**: A pressable component without visible efect of focus. + +- **PressableWithDelayToggle**: A pressable component that briefly disables then re-enables after a short delay upon pressing. + +Accessibility props are unified across all platforms. + +### Creating accessible flows +When implementing pressable components, it's essential to create accessible flows to ensure that users with disabilities can efficiently interact with the app. + +- ensure that after performing press focus is set on the correct next element - this is especially important for keyboard users who rely on focus to navigate the app. All Pressable components have a `nextFocusRef` prop that can be used to set the next focusable element after the pressable component. This prop accepts a ref to the next focusable element. For example, if you have a button that opens a modal, you can set the next focus to the first focusable element in the modal. This way, when the user presses the button, focus will be set on the first focusable element in the modal, and the user can continue navigating the modal using the keyboard. + +- size of any pressable component should be at least 44x44dp. This is the minimum size recommended by Apple and Google for touch targets. If the pressable component is smaller than `44x44dp`, it will be difficult for users with motor disabilities to interact with it. Pressable components have a `autoHitSlop` prop that can be used to automatically increase the size of the pressable component to `44x44dp`. This prop accepts a boolean value. If set to true, the pressable component will automatically increase its touchable size to 44x44dp. If set to false, the pressable component will not increase its size. By default, this prop is set to false. + +- ensure that the pressable component has a label and hint. This is especially important for users with visual disabilities who rely on screen readers to navigate the app. All Pressable components have a `accessibilitylabel` prop that can be used to set the label of the pressable component. This prop accepts a string value. All Pressable components also have a `accessibilityHint` prop that can be used to set the hint of the pressable component. This prop accepts a string value. The accessibilityHint prop is optional. If not set, the pressable component will fallback to the accessibilityLabel prop. For example, if you have a button that opens a modal, you can set the accessibilityLabel to "Open modal" and the accessibilityHint to "Opens a modal with more information". This way, when the user focuses on the button, the screen reader will read "Open modal. Opens a modal with more information". This will help the user understand what the button does and what to expect after pressing it. + +- the `enableInScreenReaderStates` prop proves invaluable when aiming to enhance the accessibility of clickable elements, particularly when desiring to enlarge the clickable area of a component, such as an entire row. This can be especially useful, for instance, when dealing with tables where only a small portion of a row, like a checkbox, might traditionally trigger an action. By employing this prop, developers can ensure that the entirety of a designated component, in this case a row, is made accessible to users employing screen readers. This creates a more inclusive user experience, allowing individuals relying on screen readers to interact with the component effortlessly. For instance, in a table, using this prop on a row component enables users to click anywhere within the row to trigger an action, significantly improving accessibility and user-friendliness. + +- ensure that the pressable component has a role. This is especially important for users with visual disabilities who rely on screen readers to navigate the app. All Pressable components have a `accessibilityRole` prop that can be used to set the role of the pressable component. + +### Testing for accessibility +It's important to test for accessibility to ensure that the created component has accessibility properties set correctly. This can be done using the following tools: + +- **iOS** +For iOS, you can use the `accessibility inspector` app to test for accessibility. You can find it in the Xcode menu under `Xcode > Open Developer Tool > Accessibility Inspector`. This app allows you to inspect the accessibility properties of any element on the screen. You can also use it to simulate different accessibility settings, such as VoiceOver, color blindness, and more. It's a great tool for testing whether created component has accessibility properties set/passed correctly. + +- **Android** +For Android, you can use the [accessibility scanner](https://support.google.com/accessibility/android/answer/6376570) app to test for accessibility. You can find it in the Google Play Store. This app allows you to inspect the accessibility properties of any element on the screen. You can also use it to simulate different accessibility settings, such as TalkBack, color blindness, and more. It's a great tool for testing whether created component has accessibility properties set correctly. The [result of the accessibility scanner](https://support.google.com/accessibility/android/answer/6376559) app has information about content labeling, implementation, touch target size and low contrast +This tool requires an installed APK to test on. + +- **Web/Desktop** +On Mac, you can use the [VoiceOver](https://www.apple.com/accessibility/mac/vision/) app to test for accessibility. You can find it in the Mac menu under `System Preferences > Accessibility > VoiceOver` or by pressing `Cmd + F5`. This app allows you to inspect the accessibility properties of any element on the screen. You can also use it to simulate different accessibility settings, such as VoiceOver, color blindness, and more. It's a great tool for testing whether created component has accessibility properties set correctly. + + +### Valuable resources +- [Apple accessibility guidelines](https://developer.apple.com/design/human-interface-guidelines/accessibility/overview/introduction/) +- [Google accessibility guidelines](https://developer.android.com/guide/topics/ui/accessibility) +- [Web accessibility guidelines](https://www.w3.org/WAI/standards-guidelines/wcag/) \ No newline at end of file diff --git a/contributingGuides/CONTRIBUTING.md b/contributingGuides/CONTRIBUTING.md index ae2b98ece85b..621673e5a487 100644 --- a/contributingGuides/CONTRIBUTING.md +++ b/contributingGuides/CONTRIBUTING.md @@ -2,7 +2,7 @@ Welcome! Thanks for checking out the New Expensify app and taking the time to contribute! ## Getting Started -If you would like to become an Expensify contributor, the first step is to read this document in its entirety. The second step is to review the README guidelines [here](https://github.com/Expensify/App/blob/main/README.md) to understand our coding philosophy and for a general overview of the code repository (i.e. how to run the app locally, testing, storage, our app philosophy, etc). Please read both documents before asking questions, as it may be covered within the documentation. +If you would like to become an Expensify contributor, the first step is to read this document in its **entirety**. The second step is to review the README guidelines [here](https://github.com/Expensify/App/blob/main/README.md) to understand our coding philosophy and for a general overview of the code repository (i.e. how to run the app locally, testing, storage, our app philosophy, etc). Please read both documents before asking questions, as it may be covered within the documentation. #### Test Accounts You can create as many accounts as needed in order to test your changes directly from [the app](https://new.expensify.com/). An initial account can be created when logging in for the first time, and additional accounts can be created by opening the "New Chat" or "Group Chat" pages via the Global Create menu, inputting a valid email or phone number, and tapping the user's avatar. @@ -47,7 +47,7 @@ Note: if you are hired for an Upwork job and have any job-specific questions, pl If you've found a vulnerability, please email security@expensify.com with the subject `Vulnerability Report` instead of creating an issue. ## Payment for Contributions -We hire and pay external contributors via Upwork.com. If you'd like to be paid for contributing or reporting a bug, please create an Upwork account, apply for an available job in [GitHub](https://github.com/Expensify/App/issues?q=is%3Aopen+is%3Aissue+label%3A%22Help+Wanted%22), and finally apply for the job in Upwork once your proposal gets selected in GitHub. If you think your compensation should be increased for a specific job, you can request a reevaluation by commenting in the Github issue where the Upwork job was posted. +We hire and pay external contributors via Upwork.com. If you'd like to be paid for contributing or reporting a bug, please create an Upwork account, apply for an available job in [GitHub](https://github.com/Expensify/App/issues?q=is%3Aopen+is%3Aissue+label%3A%22Help+Wanted%22), and finally apply for the job in Upwork once your proposal gets selected in GitHub. Please make sure your Upwork profile is **fully verified** before applying, otherwise you run the risk of not being paid. If you think your compensation should be increased for a specific job, you can request a reevaluation by commenting in the Github issue where the Upwork job was posted. Payment for your contributions and bug reports will be made no less than 7 days after the pull request is deployed to production to allow for [regression](https://github.com/Expensify/App/blob/main/contributingGuides/CONTRIBUTING.md#regressions) testing. If you have not received payment after 8 days of the PR being deployed to production, and there are no [regressions](https://github.com/Expensify/App/blob/main/contributingGuides/CONTRIBUTING.md#regressions), please add a comment to the issue mentioning the BugZero team member (Look for the melvin-bot "Triggered auto assignment to... (`Bug`)" to see who this is). @@ -89,13 +89,13 @@ It’s possible that you found a new bug that we haven’t posted as a job to th Please follow these steps to propose a job or raise a bug: 1. Check to ensure a GH issue does not already exist for this job in the [New Expensify Issue list](https://github.com/Expensify/App/issues). -2. Check to ensure the `Bug:` or `Feature Request:` was not already posted in Slack (specifically the #expensify-bugs or #expensify-open-source [Slack channels](https://github.com/Expensify/App/blob/main/contributingGuides/CONTRIBUTING.md#slack-channels)). Use your best judgement by searching for similar titles and issue descriptions. +2. Check to ensure the `Bug:` or `Feature Request:` was not already posted in Slack (specifically the #expensify-bugs or #expensify-open-source [Slack channels](https://github.com/Expensify/App/blob/main/contributingGuides/CONTRIBUTING.md#slack-channels)). Use your best judgement by searching for similar titles, words and issue descriptions. 3. If your bug or new feature matches with an existing issue, please comment on that Slack thread or GitHub issue with your findings if you think it will help solve the issue. 4. If there is no existing GitHub issue or Upwork job, check if the issue is happening on prod (as opposed to only happening on dev) 5. If the issue is just in dev then it means it's a new issue and has not been deployed to production. In this case, you should try to find the offending PR and comment in the issue tied to the PR and ask the assigned users to add the `DeployBlockerCash` label. If you can't find it, follow the reporting instructions in the next item, but note that the issue is a regression only found in dev and not in prod. -6. If the issue happens in main, staging, or production then report the issue(s) in the #expensify-bugs Slack channel, using the report bug workflow. You can do this by clicking 'Workflow > report Bug', or typing `/Report bug`. View [this guide](https://github.com/Expensify/App/blob/main/contributingGuides/HOW_TO_CREATE_A_PLAN.md) for help creating a plan when proposing a feature request. +6. If the issue happens in main, staging, or production then report the issue(s) in the #expensify-bugs Slack channel, using the report bug workflow. You can do this by clicking 'Workflow > report Bug', or typing `/Report bug`. View [this guide](https://github.com/Expensify/App/blob/main/contributingGuides/HOW_TO_CREATE_A_PLAN.md) for help creating a plan when proposing a feature request. Please verify the bug's presence on **every** platform mentioned in the bug report template, and confirm this with a screen recording.. - **Important note/reminder**: never share any information pertaining to a customer of Expensify when describing the bug. This includes, and is not limited to, a customer's name, email, and contact information. -7. The Expensify team will review your job proposal in the appropriate slack channel. If you've provided a quality proposal that we choose to implement, a GitHub issue will be created and your Slack handle will be included in the original post after `Issue reported by:` +7. The Applause team will review your job proposal in the appropriate slack channel. If you've provided a quality proposal that we choose to implement, a GitHub issue will be created and your Slack handle will be included in the original post after `Issue reported by:` 8. If an external contributor other than yourself is hired to work on the issue, you will also be hired for the same job in Upwork to receive your payout. No additional work is required. If the issue is fixed internally, a dedicated job will be created to hire and pay you after the issue is fixed. 9. Payment will be made 7 days after code is deployed to production if there are no regressions. If a regression is discovered, payment will be issued 7 days after all regressions are fixed. diff --git a/contributingGuides/STYLE.md b/contributingGuides/STYLE.md index ce59438a0681..0a88ecd7bda8 100644 --- a/contributingGuides/STYLE.md +++ b/contributingGuides/STYLE.md @@ -491,6 +491,19 @@ When writing a function component you must ALWAYS add a `displayName` property a export default Avatar; ``` +## Forwarding refs + +When forwarding a ref define named component and pass it directly to the `forwardRef`. By doing this we remove potential extra layer in React tree in form of anonymous component. + +```javascript + function FancyInput(props, ref) { + ... + return + } + + export default React.forwardRef(FancyInput) +``` + ## Stateless components vs Pure Components vs Class based components vs Render Props - When to use what? Class components are DEPRECATED. Use function components and React hooks. @@ -567,6 +580,28 @@ A `useEffect()` that does not include referenced props or state in its dependenc There are pros and cons of each, but ultimately we have standardized on using the `function` keyword to align things more with modern React conventions. There are also some minor cognitive overhead benefits in that you don't need to think about adding and removing brackets when encountering an implicit return. The `function` syntax also has the benefit of being able to be hoisted where arrow functions do not. +## How do I auto-focus a TextInput using `useFocusEffect()`? + +```javascript +const focusTimeoutRef = useRef(null); + +useFocusEffect(useCallback(() => { + focusTimeoutRef.current = setTimeout(() => textInputRef.current.focus(), CONST.ANIMATED_TRANSITION); + return () => { + if (!focusTimeoutRef.current) { + return; + } + clearTimeout(focusTimeoutRef.current); + }; +}, [])); +``` + +This works better than using `onTransitionEnd` because - +1. `onTransitionEnd` is only fired for the top card in the stack, and therefore does not fire on the new top card when popping a card off the stack. For example - pressing the back button to go from the workspace invite page to the workspace members list. +2. Using `InteractionsManager.runAfterInteractions` with `useFocusEffect` will interrupt an in-progress transition animation. + +Note - This is a solution from [this PR](https://github.com/Expensify/App/pull/26415). You can find detailed discussion in comments. + # Onyx Best Practices [Onyx Documentation](https://github.com/expensify/react-native-onyx) diff --git a/contributingGuides/TS_CHEATSHEET.md b/contributingGuides/TS_CHEATSHEET.md index df6d70b5ae90..1e330dafb7cf 100644 --- a/contributingGuides/TS_CHEATSHEET.md +++ b/contributingGuides/TS_CHEATSHEET.md @@ -43,7 +43,9 @@ - [1.2](#forwardRef) **`forwardRef`** ```ts - import { forwardRef, useRef, ReactNode } from "react"; + // CustomTextInput.tsx + + import { forwardRef, useRef, ReactNode, ForwardedRef } from "react"; import { TextInput, View } from "react-native"; export type CustomTextInputProps = { @@ -51,16 +53,18 @@ children?: ReactNode; }; - const CustomTextInput = forwardRef( - (props, ref) => { - return ( - - - {props.children} - - ); - } - ); + function CustomTextInput(props: CustomTextInputProps, ref: ForwardedRef) { + return ( + + + {props.children} + + ); + }; + + export default forwardRef(CustomTextInput); + + // ParentComponent.tsx function ParentComponent() { const ref = useRef(); diff --git a/docs/_data/_routes.yml b/docs/_data/_routes.yml index 32c8a5211ee2..c6733ac11715 100644 --- a/docs/_data/_routes.yml +++ b/docs/_data/_routes.yml @@ -1,26 +1,144 @@ home: href: home title: Welcome to ExpensifyHelp! - description: Find the answers to all of your questions about receipts, expenses, corporate cards, or anything else in the spend management universe. - -# Hubs are comprised of sections and articles. Sections contain multiple related articles, but there can be standalone articles as well -hubs: - - href: split-bills - title: Split bills - description: With only a couple of clicks, split bills with your friends or coworkers. - icon: /assets/images/paper-airplane.svg - - - href: request-money - title: Request money - icon: /assets/images/money-case.svg - description: Request money for work expenses, bills, or a night out with friends. - - - href: playbooks - title: Playbooks - icon: /assets/images/playbook.svg - description: Best practices for how to best deploy Expensify for your business - - - href: other - title: Other - description: Everything else you're looking for is right here. - icon: /assets/images/lightbulb.svg + description: Find answers by using the search bar in the left-hand menu or by clicking the version of Expensify you're using to access the relevant resources. + +platforms: + - href: expensify-classic + title: Expensify Classic + hub-title: Expensify Classic - Help & Resources + hub-description: Questions? Find the answers by clicking a Category or using the search bar located in the left-hand menu. + url: www.expensify.com + description: "Your account settings look like this:" + image: /assets/images/settings-old-dot.svg + + # Hubs are comprised of sections and articles. Sections contain multiple related articles, but there can be standalone articles as well + hubs: + - href: getting-started + title: Getting Started + icon: /assets/images/accounting.svg + description: From setting up your account to ensuring you get the most out of Expensify’s suite of features, click here to get started on streamlining your expense management journey. + + - href: account-settings + title: Account Settings + icon: /assets/images/gears.svg + description: Discover how to personalize your profile, add secondary logins, and grant delegated access to employees with our comprehensive guide on Account Settings. + + - href: bank-accounts-and-credit-cards + title: Bank Accounts & Credit Cards + icon: /assets/images/bank-card.svg + description: Find out how to connect Expensify to your financial institutions, track credit card transactions, and best practices for reconciling company cards. + + - href: billing-and-subscriptions + title: Billing & Subscriptions + icon: /assets/images/money-wings.svg + description: Here is where you can review Expensify's billing and subscription options, plan types, and payment methods. + + - href: expense-and-report-features + title: Expense & Report Features + icon: /assets/images/money-receipt.svg + description: From enabling automatic expense auditing to tracking attendees, here is where you can review tips and tutorials to streamline expense management. + + - href: expensify-card + title: Expensify Card + icon: /assets/images/hand-card.svg + description: Explore how the Expensify Card combines convenience and security to enhance everyday business transactions. Discover how to apply for, oversee, and maximize your card perks here. + + - href: exports + title: Exports + icon: /assets/images/monitor.svg + description: From exporting reports to creating custom templates, here is where you can learn more about Expensify's versatile export options. + + - href: get-paid-back + title: Get Paid Back + icon: /assets/images/money-into-wallet.svg + description: Whether you submit an expense report or an invoice, find out here how to ensure a smooth and timely payback process every time. + + - href: integrations + title: Integrations + icon: /assets/images/workflow.svg + description: Enhance Expensify’s capabilities by integrating it with your accounting or HR software. Here is where you can learn more about creating a synchronized financial management ecosystem. + + - href: manage-employees-and-report-approvals + title: Manage Employees & Report Approvals + icon: /assets/images/envelope-receipt.svg + description: Master the art of overseeing employees and reports by utilizing Expensify’s automation features and approval workflows. + + - href: policy-and-domain-settings + title: Policy & Domain Settings + icon: /assets/images/shield.svg + description: Discover how to set up and manage policies, define user permissions, and implement compliance rules to maintain a secure and compliant financial management landscape. + + - href: send-payments + title: Send Payments + icon: /assets/images/money-wings.svg + description: Uncover step-by-step guidance on sending direct reimbursements to employees, paying an invoice to a vendor, and utilizing third-party payment options. + + - href: new-expensify + title: New Expensify + hub-title: New Expensify - Help & Resources + hub-description: Questions? Find the answers by clicking a Category or using the search bar located in the left-hand menu. + url: new.expensify.com + description: "Your account settings look like this:" + image: /assets/images/settings-new-dot.svg + + hubs: + - href: getting-started + title: Getting Started + icon: /assets/images/accounting.svg + description: From setting up your account to ensuring you get the most out of Expensify’s suite of features, click here to get started on streamlining your expense management journey. + + - href: account-settings + title: Account Settings + icon: /assets/images/gears.svg + description: Discover how to personalize your profile, add secondary logins, and grant delegated access to employees with our comprehensive guide on Account Settings. + + - href: bank-accounts-and-credit-cards + title: Bank Accounts & Credit Cards + icon: /assets/images/bank-card.svg + description: Find out how to connect Expensify to your financial institutions, track credit card transactions, and best practices for reconciling company cards. + + - href: billing-and-plan-types + title: Billing & Plan Types + icon: /assets/images/money-wings.svg + description: Here is where you can review Expensify's billing and subscription options, plan types, and payment methods. + + - href: expense-and-report-features + title: Expense & Report Features + icon: /assets/images/money-receipt.svg + description: From enabling automatic expense auditing to tracking attendees, here is where you can review tips and tutorials to streamline expense management. + + - href: expensify-card + title: Expensify Card + icon: /assets/images/hand-card.svg + description: Explore how the Expensify Card combines convenience and security to enhance everyday business transactions. Discover how to apply for, oversee, and maximize your card perks here. + + - href: exports + title: Exports + icon: /assets/images/monitor.svg + description: From exporting reports to creating custom templates, here is where you can learn more about Expensify's versatile export options. + + - href: get-paid-back + title: Get Paid Back + icon: /assets/images/money-into-wallet.svg + description: Whether you submit an expense report or an invoice, find out here how to ensure a smooth and timely payback process every time. + + - href: integrations + title: Integrations + icon: /assets/images/workflow.svg + description: Enhance Expensify’s capabilities by integrating it with your accounting or HR software. Here is where you can learn more about creating a synchronized financial management ecosystem. + + - href: manage-employees-and-report-approvals + title: Manage Employees & Report Approvals + icon: /assets/images/envelope-receipt.svg + description: Master the art of overseeing employees and reports by utilizing Expensify’s automation features and approval workflows. + + - href: send-payments + title: Send Payments + icon: /assets/images/money-wings.svg + description: Uncover step-by-step guidance on sending direct reimbursements to employees, paying an invoice to a vendor, and utilizing third-party payment options. + + - href: workspace-and-domain-settings + title: Workspace & Domain Settings + icon: /assets/images/shield.svg + description: Discover how to set up and manage your workspace, define user permissions, and implement domain-level rules. diff --git a/docs/_includes/article-card.html b/docs/_includes/article-card.html index a088e5e406db..b66affebb4ae 100644 --- a/docs/_includes/article-card.html +++ b/docs/_includes/article-card.html @@ -1,6 +1,6 @@ - +
-

{{ include.title }}

+

{{ include.title }}

diff --git a/docs/_includes/hub-card.html b/docs/_includes/hub-card.html index 36bf3bc36e6a..859ee0004394 100644 --- a/docs/_includes/hub-card.html +++ b/docs/_includes/hub-card.html @@ -1,8 +1,8 @@ -{% assign hub = site.data.routes.hubs | where: "href", include.href | first %} - - +{% assign hub = include.hub %} +{% assign platform = include.platform %} +
-
+
{{ hub.href }}
diff --git a/docs/_includes/hub.html b/docs/_includes/hub.html index acdc901a38f6..7f1e25243c09 100644 --- a/docs/_includes/hub.html +++ b/docs/_includes/hub.html @@ -1,5 +1,8 @@ -{% assign activeHub = page.url | remove: "/hubs/" | remove: ".html" %} -{% assign hub = site.data.routes.hubs | where: "href", activeHub | first %} +{% assign activePlatform = page.url | replace: '/', ' ' | truncatewords: 1 | remove:'...' %} +{% assign platform = site.data.routes.platforms | where: "href", activePlatform | first %} + +{% assign activeHub = page.url | remove: activePlatform | remove: "/hubs/" | remove: "/" | remove: ".html" %} +{% assign hub = platform.hubs | where: "href", activeHub | first %}

{{ hub.title }} @@ -9,27 +12,13 @@

{{ hub.description }}

-{% for section in hub.sections %} -
-

- {{ section.title }} -

- -
- {% for article in section.articles %} - {% assign article_href = section.href | append: '/' | append: article.href %} - {% include article-card.html hub=hub.href href=article_href title=article.title %} - {% endfor %} -
-
-{% endfor %} - -{% if hub.articles %} -
-
- {% for article in hub.articles %} - {% include article-card.html hub=hub.href href=article.href title=article.title %} - {% endfor %} -
-
-{% endif %} +
+
+ {% for section in hub.sections %} + {% include section-card.html platform=activePlatform hub=hub.href section=section.href title=section.title %} + {% endfor %} + {% for article in hub.articles %} + {% include article-card.html hub=hub.href href=article.href title=article.title platform=activePlatform %} + {% endfor %} +
+
diff --git a/docs/_includes/lhn-article-link.html b/docs/_includes/lhn-article-link.html index f9c4f31f0dbe..91c0de4aacce 100644 --- a/docs/_includes/lhn-article-link.html +++ b/docs/_includes/lhn-article-link.html @@ -1,5 +1,5 @@
  • - + {{ include.title }}
  • diff --git a/docs/_includes/lhn-template.html b/docs/_includes/lhn-template.html index 0473e5da9e9c..80302f33f52e 100644 --- a/docs/_includes/lhn-template.html +++ b/docs/_includes/lhn-template.html @@ -1,4 +1,13 @@ -{% assign activeHub = page.url | remove: "/hubs/" | remove: ".html" %} +{% assign urlArray = page.url | replace: '/', ' ' | split: " " %} + +{% assign activePlatform = urlArray[0] %} +{% assign platform = site.data.routes.platforms | where: "href", activePlatform | first %} + +{% assign activeHub = urlArray[2] %} +{% assign hub = platform.hubs | where: "href", activeHub | first %} + +{% assign activeSection = urlArray[3] | remove: ".html" %} +{% assign section = hub.sections | where: "href", activeSection | first %}
      - {% for hub in site.data.routes.hubs %} - {% if hub.href == activeHub %} + {% for platform in site.data.routes.platforms %} + {% if platform.href == activePlatform %}
    • - -
        - - {% for section in hub.sections %} + {{ platform.title }} + + {% for hub in platform.hubs %} +
          + {% if hub.href == activeHub %} + + + {{ hub.title }} + +
            + {% for section in hub.sections %} +
          • + {% if section.href == activeSection %} + + + {{ section.title }} + +
              + {% for article in section.articles %} + {% assign article_href = section.href | append: '/' | append: article.href %} + {% include lhn-article-link.html platform=activePlatform hub=hub.href href=article_href title=article.title %} + {% endfor %} +
            + {% else %} + + + {{ section.title }} + + {% endif %} + +
          • + {% endfor %} + + {% for article in hub.articles %} + {% include lhn-article-link.html platform=activePlatform hub=hub.href href=article.href title=article.title %} + {% endfor %} +
          + {% else %}
        • - {{ section.title }} -
            - {% for article in section.articles %} - {% assign article_href = section.href | append: '/' | append: article.href %} - {% include lhn-article-link.html hub=hub.href href=article_href title=article.title %} - {% endfor %} -
          + + + {{ hub.title }} +
        • - {% endfor %} - - - {% for article in hub.articles %} - {% include lhn-article-link.html hub=hub.href href=article.href title=article.title %} - {% endfor %} + {% endif %}
        + {% endfor %} + {% else %}
      • - + - {{ hub.title }} + {{ platform.title }}
      • {% endif %} diff --git a/docs/_includes/platform-card.html b/docs/_includes/platform-card.html new file mode 100644 index 000000000000..7123f18a679a --- /dev/null +++ b/docs/_includes/platform-card.html @@ -0,0 +1,22 @@ +{% assign platform = site.data.routes.platforms | where: "href", include.href | first %} + + +
        +
        +
        +
        +

        {{ platform.title }}

        +

        {{ platform.url }}

        +
        +
        + +
        +
        + +

        {{ platform.description }}

        +
        +
        + {{ platform.href }} +
        +
        +
        diff --git a/docs/_includes/platform.html b/docs/_includes/platform.html new file mode 100644 index 000000000000..6aa88f9208ae --- /dev/null +++ b/docs/_includes/platform.html @@ -0,0 +1,18 @@ +{% assign selectedPlatform = page.url | remove: "/hubs/" | remove: "/" | remove: ".html" %} +{% assign platform = site.data.routes.platforms | where: "href", selectedPlatform | first %} +
        +

        {{ platform.hub-title }}

        + +

        {{ platform.hub-description }}

        + +
        + {% for hub in platform.hubs %} + {% include hub-card.html hub=hub platform=selectedPlatform %} + {% endfor %} +
        + +
        + + {% include floating-concierge-button.html id="floating-concierge-button-global" %} +
        +
        diff --git a/docs/_includes/section-card.html b/docs/_includes/section-card.html new file mode 100644 index 000000000000..9500983d4d28 --- /dev/null +++ b/docs/_includes/section-card.html @@ -0,0 +1,8 @@ + +
        +

        {{ include.title }}

        +
        +
        + +
        +
        diff --git a/docs/_includes/section.html b/docs/_includes/section.html new file mode 100644 index 000000000000..786e7d997462 --- /dev/null +++ b/docs/_includes/section.html @@ -0,0 +1,23 @@ +{% assign urlArray = page.url | replace: '/', ' ' | split: " " %} + +{% assign activePlatform = urlArray[0] %} +{% assign platform = site.data.routes.platforms | where: "href", activePlatform | first %} + +{% assign activeHub = urlArray[2] %} +{% assign hub = platform.hubs | where: "href", activeHub | first %} + +{% assign activeSection = urlArray[3] | remove: ".html" %} +{% assign section = hub.sections | where: "href", activeSection | first %} + +

        + {{ section.title }} +

        + +
        +
        + {% for article in section.articles %} + {% assign article_href = section.href | append: '/' | append: article.href %} + {% include article-card.html hub=hub.href href=article_href title=article.title platform=activePlatform %} + {% endfor %} +
        +
        diff --git a/docs/_layouts/default.html b/docs/_layouts/default.html index 209d14de0f48..de3fbc203243 100644 --- a/docs/_layouts/default.html +++ b/docs/_layouts/default.html @@ -96,12 +96,5 @@

        Didn't find what you were looking for?

        {% include footer.html %}

    - - - diff --git a/docs/_sass/_main.scss b/docs/_sass/_main.scss index bc9d19bfca11..6e4095569a6d 100644 --- a/docs/_sass/_main.scss +++ b/docs/_sass/_main.scss @@ -299,7 +299,6 @@ button { } .selected { - cursor: auto; font-weight: bold; color: $color-text; } @@ -457,6 +456,15 @@ button { } } + +.platform-cards-group { + @extend .cards-group; + + @include breakpoint($breakpoint-desktop) { + grid-template-columns: 33.33% 33.33% 33.33%; + } +} + .card { display: flex; flex-wrap: nowrap; @@ -476,21 +484,55 @@ button { flex-basis:100%; } - .left-icon { + .body { display: flex; - align-items: center; - padding-right: 28px; + flex-wrap: nowrap; + flex-direction: column; + flex-grow: 2; + } - img { - width: 64px; - } + h3.title { + font-family: "ExpensifyNewKansas", "Helvetica Neue", "Helvetica", Arial, sans-serif; + } + + h3.title, + h4.title { + padding: 0; + margin: 0; } + p.description, + p.url { + margin: 0; + font-weight: normal; + } +} + +.article-card { + @extend .card; + .right-icon { display: flex; align-items: center; padding-left: 16px; } +} + +.platform-card { + @extend .card; + .row { + flex-direction: column; + } + + .platform-screenshot { + display: flex; + align-items: center; + + img { + border-radius: 12px; + width: 100%; + } + } .submit-button { display: flex; @@ -505,27 +547,62 @@ button { } .body { - display: flex; - flex-wrap: nowrap; - flex-direction: column; - flex-grow: 2; - } + .header { + display: flex; + align-items: center; + justify-content: space-between; - h3.title { - padding: 0; - margin: 0; + .select-button { + display: flex; + .success { + align-items: flex-end; + font-size: 0.8em; + } + } + } + } + h3.title, + h4.title { &.with-margin { margin: 0 0 4px 0; } } - + h3.title { + font-size: 1.4em; + font-weight: normal; + } p.description { + padding: 20px 0 20px 0; + } + + p.url { padding: 0; - margin: 0; + font-size: 0.8em; + color: $color-gray-label; + } +} + +.hub-card { + @extend .card; + padding: 24px; + + .row { + flex-direction: column; + } + + h3.title { + font-size: 1.2em; font-weight: normal; + &.with-margin { + margin: 20px 0 8px 0; + } + } + + p.description { + padding: 0; &.with-min-height { min-height: 68px; diff --git a/docs/_sass/_search-bar.scss b/docs/_sass/_search-bar.scss index ce085878af46..a5cc8ae2ff20 100644 --- a/docs/_sass/_search-bar.scss +++ b/docs/_sass/_search-bar.scss @@ -23,14 +23,25 @@ $color-gray-label: $color-gray-label; #sidebar-search { background-color: $color-appBG; width: 375px; - height: 100vh; position: fixed; - display: block; + display: flex; + flex-direction: column; + bottom: 0; top: 0; right: 0; z-index: 2; } +#sidebar-search > div:last-child { + flex-grow: 1; + overflow-y: auto; + -ms-overflow-style: none; + scrollbar-width: none; + &::-webkit-scrollbar { + display: none; + } +} + @media only screen and (max-width: $breakpoint-tablet) { #sidebar-search { width: 100%; @@ -156,10 +167,6 @@ label.search-label { background-color: $color-appBG; border: $color-appBG; font-family: "ExpensifyNeue", "Helvetica Neue", "Helvetica", Arial, sans-serif !important; - max-height: 80vh; - overflow-y: scroll; - -ms-overflow-style: none; - scrollbar-width: none; } /* Hide the scrollbar */ diff --git a/docs/articles/expensify-classic/account-settings/Account-Access.md b/docs/articles/expensify-classic/account-settings/Account-Access.md new file mode 100644 index 000000000000..b3126201715f --- /dev/null +++ b/docs/articles/expensify-classic/account-settings/Account-Access.md @@ -0,0 +1,5 @@ +--- +title: Account Access +description: Account Access +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/account-settings/Close-Account.md b/docs/articles/expensify-classic/account-settings/Close-Account.md new file mode 100644 index 000000000000..5e18490fc357 --- /dev/null +++ b/docs/articles/expensify-classic/account-settings/Close-Account.md @@ -0,0 +1,5 @@ +--- +title: Close Account +description: Close Account +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/account-settings/Merge-Accounts.md b/docs/articles/expensify-classic/account-settings/Merge-Accounts.md new file mode 100644 index 000000000000..073c74346d75 --- /dev/null +++ b/docs/articles/expensify-classic/account-settings/Merge-Accounts.md @@ -0,0 +1,5 @@ +--- +title: Merge Accounts +description: Merge Accounts +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/account-settings/Preferences.md b/docs/articles/expensify-classic/account-settings/Preferences.md new file mode 100644 index 000000000000..532da4d8a986 --- /dev/null +++ b/docs/articles/expensify-classic/account-settings/Preferences.md @@ -0,0 +1,5 @@ +--- +title: Preferences +description: Preferences +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/account-settings/Profile-Settings.md b/docs/articles/expensify-classic/account-settings/Profile-Settings.md new file mode 100644 index 000000000000..3b2a0b830926 --- /dev/null +++ b/docs/articles/expensify-classic/account-settings/Profile-Settings.md @@ -0,0 +1,5 @@ +--- +title: Profile Settings +description: Profile Settings +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/Global-Reimbursement.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/Global-Reimbursement.md new file mode 100644 index 000000000000..073d3a9bd700 --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/Global-Reimbursement.md @@ -0,0 +1,5 @@ +--- +title: Global Reimbursement +description: Global Reimbursement +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/Personal-Credit-Cards.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/Personal-Credit-Cards.md new file mode 100644 index 000000000000..f89729b69586 --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/Personal-Credit-Cards.md @@ -0,0 +1,5 @@ +--- +title: Personal Credit Cards +description: Personal Credit Cards +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/business-bank-accounts/Business-Bank-Accounts-AUD.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/business-bank-accounts/Business-Bank-Accounts-AUD.md new file mode 100644 index 000000000000..7c789942a2b3 --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/business-bank-accounts/Business-Bank-Accounts-AUD.md @@ -0,0 +1,5 @@ +--- +title: Business Bank Accounts - AUD +description: Business Bank Accounts - AUD +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/business-bank-accounts/Business-Bank-Accounts-USD.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/business-bank-accounts/Business-Bank-Accounts-USD.md new file mode 100644 index 000000000000..375b00d62eac --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/business-bank-accounts/Business-Bank-Accounts-USD.md @@ -0,0 +1,5 @@ +--- +title: Business Bank Accounts - USD +description: Business Bank Accounts - USD +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/ANZ.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/ANZ.md new file mode 100644 index 000000000000..7e6a76ecee24 --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/ANZ.md @@ -0,0 +1,6 @@ +--- +title: ANZ +description: A guide to integrate with your ANZ card +--- +## Resource Coming Soon! +Coming Soon!! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Brex.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Brex.md new file mode 100644 index 000000000000..a060e37146a5 --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Brex.md @@ -0,0 +1,5 @@ +--- +title: Brex +description: Brex +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/CSV-Import.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/CSV-Import.md new file mode 100644 index 000000000000..6debce6240ff --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/CSV-Import.md @@ -0,0 +1,5 @@ +--- +title: CSV Import +description: CSV Import +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Commercial-Card-Feeds.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Commercial-Card-Feeds.md new file mode 100644 index 000000000000..25d11561755d --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Commercial-Card-Feeds.md @@ -0,0 +1,5 @@ +--- +title: Commercial Card Feeds +description: Commercial Card Feeds +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Connect-Company-Cards.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Connect-Company-Cards.md new file mode 100644 index 000000000000..112c3b9617c9 --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Connect-Company-Cards.md @@ -0,0 +1,5 @@ +--- +title: Connect Company Cards +description: Connect Company Cards +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Direct-Bank-Connections.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Direct-Bank-Connections.md new file mode 100644 index 000000000000..f1d939ca9c89 --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Direct-Bank-Connections.md @@ -0,0 +1,5 @@ +--- +title: Direct Bank Connections +description: Direct Bank Connections +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Export-To-GL-Accounts.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Export-To-GL-Accounts.md new file mode 100644 index 000000000000..85b534338b53 --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Export-To-GL-Accounts.md @@ -0,0 +1,5 @@ +--- +title: Export to GL Accounts +description: Export to GL Accounts +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Reconciliation.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Reconciliation.md new file mode 100644 index 000000000000..b51329f2a803 --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Reconciliation.md @@ -0,0 +1,5 @@ +--- +title: Reconciliation +description: Reconciliation +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Troubleshooting.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Troubleshooting.md new file mode 100644 index 000000000000..e3d1307e6a05 --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/company-cards/Troubleshooting.md @@ -0,0 +1,5 @@ +--- +title: Troubleshooting +description: Troubleshooting +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/deposit-accounts/Deposit-Accounts-AUS.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/deposit-accounts/Deposit-Accounts-AUS.md new file mode 100644 index 000000000000..61e6dfd95e38 --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/deposit-accounts/Deposit-Accounts-AUS.md @@ -0,0 +1,5 @@ +--- +title: Deposit Accounts - AUD +description: Deposit Accounts - AUD +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/bank-accounts-and-credit-cards/deposit-accounts/Deposit-Accounts-USD.md b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/deposit-accounts/Deposit-Accounts-USD.md new file mode 100644 index 000000000000..19010be95980 --- /dev/null +++ b/docs/articles/expensify-classic/bank-accounts-and-credit-cards/deposit-accounts/Deposit-Accounts-USD.md @@ -0,0 +1,5 @@ +--- +title: Deposit Accounts - USD +description: Deposit Accounts - USD +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/billing-and-subscriptions/Annual-Subscription.md b/docs/articles/expensify-classic/billing-and-subscriptions/Annual-Subscription.md new file mode 100644 index 000000000000..8e2aa7d4a377 --- /dev/null +++ b/docs/articles/expensify-classic/billing-and-subscriptions/Annual-Subscription.md @@ -0,0 +1,5 @@ +--- +title: Annual Subscription +description: Annual Subscription +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/billing-and-subscriptions/Billing-Owner.md b/docs/articles/expensify-classic/billing-and-subscriptions/Billing-Owner.md new file mode 100644 index 000000000000..acb29d91e1d8 --- /dev/null +++ b/docs/articles/expensify-classic/billing-and-subscriptions/Billing-Owner.md @@ -0,0 +1,5 @@ +--- +title: Billing-Owner +description: Billing-Owner +--- +## Resource Coming Soon! \ No newline at end of file diff --git a/docs/articles/expensify-classic/billing-and-subscriptions/Change-Plan-Or-Subscription.md b/docs/articles/expensify-classic/billing-and-subscriptions/Change-Plan-Or-Subscription.md new file mode 100644 index 000000000000..8ce4283dd17d --- /dev/null +++ b/docs/articles/expensify-classic/billing-and-subscriptions/Change-Plan-Or-Subscription.md @@ -0,0 +1,5 @@ +--- +title: Change Plan or Subscription +description: Change Plan or Subscription +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/billing-and-subscriptions/Consolidated-Domain-Billing.md b/docs/articles/expensify-classic/billing-and-subscriptions/Consolidated-Domain-Billing.md new file mode 100644 index 000000000000..24edc553bd29 --- /dev/null +++ b/docs/articles/expensify-classic/billing-and-subscriptions/Consolidated-Domain-Billing.md @@ -0,0 +1,5 @@ +--- +title: Consolidated Domain Billing +description: Consolidated Domain Billing +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/billing-and-subscriptions/Free-Trial.md b/docs/articles/expensify-classic/billing-and-subscriptions/Free-Trial.md new file mode 100644 index 000000000000..e08aaa3d6094 --- /dev/null +++ b/docs/articles/expensify-classic/billing-and-subscriptions/Free-Trial.md @@ -0,0 +1,5 @@ +--- +title: Free Trial +description: Free Trial +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/billing-and-subscriptions/Individual-Subscription.md b/docs/articles/expensify-classic/billing-and-subscriptions/Individual-Subscription.md new file mode 100644 index 000000000000..1ace758978aa --- /dev/null +++ b/docs/articles/expensify-classic/billing-and-subscriptions/Individual-Subscription.md @@ -0,0 +1,5 @@ +--- +title: Individual Subscription +description: Individual Subscription +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/billing-and-subscriptions/Overview.md b/docs/articles/expensify-classic/billing-and-subscriptions/Overview.md new file mode 100644 index 000000000000..963186916f01 --- /dev/null +++ b/docs/articles/expensify-classic/billing-and-subscriptions/Overview.md @@ -0,0 +1,5 @@ +--- +title: Overview +description: Overview +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/billing-and-subscriptions/Pay-Per-Use-Subscription.md b/docs/articles/expensify-classic/billing-and-subscriptions/Pay-Per-Use-Subscription.md new file mode 100644 index 000000000000..77aca2a01678 --- /dev/null +++ b/docs/articles/expensify-classic/billing-and-subscriptions/Pay-Per-Use-Subscription.md @@ -0,0 +1,5 @@ +--- +title: Pay-per-use Subscription +description: Pay-per-use Subscription +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/billing-and-subscriptions/Payment-Card.md b/docs/articles/expensify-classic/billing-and-subscriptions/Payment-Card.md new file mode 100644 index 000000000000..41a1fb96f56f --- /dev/null +++ b/docs/articles/expensify-classic/billing-and-subscriptions/Payment-Card.md @@ -0,0 +1,5 @@ +--- +title: Payment Card +description: Payment Card +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/billing-and-subscriptions/Tax-Exempt.md b/docs/articles/expensify-classic/billing-and-subscriptions/Tax-Exempt.md new file mode 100644 index 000000000000..c4948b5b3083 --- /dev/null +++ b/docs/articles/expensify-classic/billing-and-subscriptions/Tax-Exempt.md @@ -0,0 +1,5 @@ +--- +title: Tax Exempt +description: Tax Exempt +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expense-and-report-features/Attendee-Tracking.md b/docs/articles/expensify-classic/expense-and-report-features/Attendee-Tracking.md new file mode 100644 index 000000000000..a5b0b26b2610 --- /dev/null +++ b/docs/articles/expensify-classic/expense-and-report-features/Attendee-Tracking.md @@ -0,0 +1,5 @@ +--- +title: Attendee Tracking +description: Attendee Tracking +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expense-and-report-features/Currency.md b/docs/articles/expensify-classic/expense-and-report-features/Currency.md new file mode 100644 index 000000000000..e5c9096fa610 --- /dev/null +++ b/docs/articles/expensify-classic/expense-and-report-features/Currency.md @@ -0,0 +1,5 @@ +--- +title: Currency +description: Currency +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expense-and-report-features/Expense-Rules.md b/docs/articles/expensify-classic/expense-and-report-features/Expense-Rules.md new file mode 100644 index 000000000000..304c93d1da6d --- /dev/null +++ b/docs/articles/expensify-classic/expense-and-report-features/Expense-Rules.md @@ -0,0 +1,5 @@ +--- +title: Expense Rules +description: Expense Rules +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expense-and-report-features/Expense-Types.md b/docs/articles/expensify-classic/expense-and-report-features/Expense-Types.md new file mode 100644 index 000000000000..3f2e49952c4a --- /dev/null +++ b/docs/articles/expensify-classic/expense-and-report-features/Expense-Types.md @@ -0,0 +1,5 @@ +--- +title: Expense Types +description: Expense Types +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expense-and-report-features/Report-Comments.md b/docs/articles/expensify-classic/expense-and-report-features/Report-Comments.md new file mode 100644 index 000000000000..b7ed120fb28b --- /dev/null +++ b/docs/articles/expensify-classic/expense-and-report-features/Report-Comments.md @@ -0,0 +1,5 @@ +--- +title: Report Comments +description: Report Comments +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expense-and-report-features/The-Expenses-Page.md b/docs/articles/expensify-classic/expense-and-report-features/The-Expenses-Page.md new file mode 100644 index 000000000000..f30dde9efc3d --- /dev/null +++ b/docs/articles/expensify-classic/expense-and-report-features/The-Expenses-Page.md @@ -0,0 +1,5 @@ +--- +title: The Expenses Page +description: The Expenses Page +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expense-and-report-features/The-Reports-Page.md b/docs/articles/expensify-classic/expense-and-report-features/The-Reports-Page.md new file mode 100644 index 000000000000..e72abfcad51a --- /dev/null +++ b/docs/articles/expensify-classic/expense-and-report-features/The-Reports-Page.md @@ -0,0 +1,5 @@ +--- +title: The Reports Page +description: The Reports Page +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expensify-card/Auto-Reconciliation.md b/docs/articles/expensify-classic/expensify-card/Auto-Reconciliation.md new file mode 100644 index 000000000000..85202835a0e4 --- /dev/null +++ b/docs/articles/expensify-classic/expensify-card/Auto-Reconciliation.md @@ -0,0 +1,5 @@ +--- +title: Auto-reconciliation +description: Auto-reconciliation +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expensify-card/CPA-Card.md b/docs/articles/expensify-classic/expensify-card/CPA-Card.md new file mode 100644 index 000000000000..dfc1e71192db --- /dev/null +++ b/docs/articles/expensify-classic/expensify-card/CPA-Card.md @@ -0,0 +1,5 @@ +--- +title: CPA Card +description: CPA Card +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expensify-card/Card-Settings.md b/docs/articles/expensify-classic/expensify-card/Card-Settings.md new file mode 100644 index 000000000000..ab212354974a --- /dev/null +++ b/docs/articles/expensify-classic/expensify-card/Card-Settings.md @@ -0,0 +1,5 @@ +--- +title: Card Settings +description: Card Settings +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expensify-card/Connect-To-Indirect-Integration.md b/docs/articles/expensify-classic/expensify-card/Connect-To-Indirect-Integration.md new file mode 100644 index 000000000000..9888edd139ac --- /dev/null +++ b/docs/articles/expensify-classic/expensify-card/Connect-To-Indirect-Integration.md @@ -0,0 +1,5 @@ +--- +title: Connect to Indirect Integration +description: Connect to Indirect Integration +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expensify-card/File-A-Dispute.md b/docs/articles/expensify-classic/expensify-card/File-A-Dispute.md new file mode 100644 index 000000000000..694bce3da059 --- /dev/null +++ b/docs/articles/expensify-classic/expensify-card/File-A-Dispute.md @@ -0,0 +1,5 @@ +--- +title: File a Dispute +description: File a Dispute +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expensify-card/Get-The-Card.md b/docs/articles/expensify-classic/expensify-card/Get-The-Card.md new file mode 100644 index 000000000000..e5233a3732a3 --- /dev/null +++ b/docs/articles/expensify-classic/expensify-card/Get-The-Card.md @@ -0,0 +1,5 @@ +--- +title: Get the Card +description: Get the Card +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/expensify-card/Statements.md b/docs/articles/expensify-classic/expensify-card/Statements.md new file mode 100644 index 000000000000..b48d303a1a9b --- /dev/null +++ b/docs/articles/expensify-classic/expensify-card/Statements.md @@ -0,0 +1,5 @@ +--- +title: Statements +description: Statements +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/exports/Custom-Templates.md b/docs/articles/expensify-classic/exports/Custom-Templates.md new file mode 100644 index 000000000000..e01450a730cf --- /dev/null +++ b/docs/articles/expensify-classic/exports/Custom-Templates.md @@ -0,0 +1,5 @@ +--- +title: Custom Templates +description: Custom Templates +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/exports/Default-Export-Templates.md b/docs/articles/expensify-classic/exports/Default-Export-Templates.md new file mode 100644 index 000000000000..7650cff38946 --- /dev/null +++ b/docs/articles/expensify-classic/exports/Default-Export-Templates.md @@ -0,0 +1,5 @@ +--- +title: Default Export Templates +description: Default Export Templates +--- +## Resource Coming Soon! diff --git a/docs/articles/other/Insights.md b/docs/articles/expensify-classic/exports/Insights.md similarity index 100% rename from docs/articles/other/Insights.md rename to docs/articles/expensify-classic/exports/Insights.md diff --git a/docs/articles/expensify-classic/get-paid-back/Mileage.md b/docs/articles/expensify-classic/get-paid-back/Mileage.md new file mode 100644 index 000000000000..248e80e1c115 --- /dev/null +++ b/docs/articles/expensify-classic/get-paid-back/Mileage.md @@ -0,0 +1,5 @@ +--- +title: Mileage +description: Mileage +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/get-paid-back/Per-Diem.md b/docs/articles/expensify-classic/get-paid-back/Per-Diem.md new file mode 100644 index 000000000000..780e5969c441 --- /dev/null +++ b/docs/articles/expensify-classic/get-paid-back/Per-Diem.md @@ -0,0 +1,5 @@ +--- +title: Per Diem +description: Per Diem +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/get-paid-back/Third-Party-Payments.md b/docs/articles/expensify-classic/get-paid-back/Third-Party-Payments.md new file mode 100644 index 000000000000..a8cddcdfdd42 --- /dev/null +++ b/docs/articles/expensify-classic/get-paid-back/Third-Party-Payments.md @@ -0,0 +1,5 @@ +--- +title: Third Party Payments +description: Third Party Payments +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/get-paid-back/Trips.md b/docs/articles/expensify-classic/get-paid-back/Trips.md new file mode 100644 index 000000000000..7efba1875a90 --- /dev/null +++ b/docs/articles/expensify-classic/get-paid-back/Trips.md @@ -0,0 +1,5 @@ +--- +title: Trips +description: Trips +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/get-paid-back/expenses/Apply-Tax.md b/docs/articles/expensify-classic/get-paid-back/expenses/Apply-Tax.md new file mode 100644 index 000000000000..36e0a2194d24 --- /dev/null +++ b/docs/articles/expensify-classic/get-paid-back/expenses/Apply-Tax.md @@ -0,0 +1,5 @@ +--- +title: Apply Tax +description: Apply Tax +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/get-paid-back/expenses/Create-Expenses.md b/docs/articles/expensify-classic/get-paid-back/expenses/Create-Expenses.md new file mode 100644 index 000000000000..8323be7b8e3f --- /dev/null +++ b/docs/articles/expensify-classic/get-paid-back/expenses/Create-Expenses.md @@ -0,0 +1,5 @@ +--- +title: Create Expenses +description: Create Expenses +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/get-paid-back/expenses/Merge-Expenses.md b/docs/articles/expensify-classic/get-paid-back/expenses/Merge-Expenses.md new file mode 100644 index 000000000000..e7705a32f215 --- /dev/null +++ b/docs/articles/expensify-classic/get-paid-back/expenses/Merge-Expenses.md @@ -0,0 +1,5 @@ +--- +title: Merge Expenses +description: Merge Expenses +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/get-paid-back/expenses/Upload-Receipts.md b/docs/articles/expensify-classic/get-paid-back/expenses/Upload-Receipts.md new file mode 100644 index 000000000000..b71fd1a3c8bf --- /dev/null +++ b/docs/articles/expensify-classic/get-paid-back/expenses/Upload-Receipts.md @@ -0,0 +1,5 @@ +--- +title: Upload Receipts +description: Upload Receipts +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/get-paid-back/reports/Create-A-Report.md b/docs/articles/expensify-classic/get-paid-back/reports/Create-A-Report.md new file mode 100644 index 000000000000..fb4f756b2820 --- /dev/null +++ b/docs/articles/expensify-classic/get-paid-back/reports/Create-A-Report.md @@ -0,0 +1,5 @@ +--- +title: Create a Report +description: Create a Report +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/get-paid-back/reports/Reimbursements.md b/docs/articles/expensify-classic/get-paid-back/reports/Reimbursements.md new file mode 100644 index 000000000000..c2cc25b32373 --- /dev/null +++ b/docs/articles/expensify-classic/get-paid-back/reports/Reimbursements.md @@ -0,0 +1,5 @@ +--- +title: Reimbursements +description: Reimbursements +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/getting-started/Best-Practices.md b/docs/articles/expensify-classic/getting-started/Best-Practices.md new file mode 100644 index 000000000000..b02ea9d68fe6 --- /dev/null +++ b/docs/articles/expensify-classic/getting-started/Best-Practices.md @@ -0,0 +1,5 @@ +--- +title: Best Practices +description: Best Practices +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/getting-started/Employees.md b/docs/articles/expensify-classic/getting-started/Employees.md new file mode 100644 index 000000000000..6d3c2dc705e1 --- /dev/null +++ b/docs/articles/expensify-classic/getting-started/Employees.md @@ -0,0 +1,5 @@ +--- +title: Employees +description: Employees +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/getting-started/Individual-Users.md b/docs/articles/expensify-classic/getting-started/Individual-Users.md new file mode 100644 index 000000000000..de7a527df010 --- /dev/null +++ b/docs/articles/expensify-classic/getting-started/Individual-Users.md @@ -0,0 +1,5 @@ +--- +title: Individual Users +description: Individual Users +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/getting-started/Invite-Employees.md b/docs/articles/expensify-classic/getting-started/Invite-Employees.md new file mode 100644 index 000000000000..73dc7b8274f0 --- /dev/null +++ b/docs/articles/expensify-classic/getting-started/Invite-Employees.md @@ -0,0 +1,5 @@ +--- +title: Invite Employees +description: Invite Employees +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/getting-started/Mobile-App.md b/docs/articles/expensify-classic/getting-started/Mobile-App.md new file mode 100644 index 000000000000..7fa57abbdf61 --- /dev/null +++ b/docs/articles/expensify-classic/getting-started/Mobile-App.md @@ -0,0 +1,5 @@ +--- +title: Using the App +description: Using the App +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/getting-started/Plan-Types.md b/docs/articles/expensify-classic/getting-started/Plan-Types.md new file mode 100644 index 000000000000..f0323947ee12 --- /dev/null +++ b/docs/articles/expensify-classic/getting-started/Plan-Types.md @@ -0,0 +1,5 @@ +--- +title: Plan-Types +description: Plan-Types +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/getting-started/Policy-Admins.md b/docs/articles/expensify-classic/getting-started/Policy-Admins.md new file mode 100644 index 000000000000..484350f101a5 --- /dev/null +++ b/docs/articles/expensify-classic/getting-started/Policy-Admins.md @@ -0,0 +1,5 @@ +--- +title: Policy Admins +description: Policy Admins +--- +## Resource Coming Soon! diff --git a/docs/articles/other/Referral-Program.md b/docs/articles/expensify-classic/getting-started/Referral-Program.md similarity index 98% rename from docs/articles/other/Referral-Program.md rename to docs/articles/expensify-classic/getting-started/Referral-Program.md index 1faff1c9ec4f..683e93d0277a 100644 --- a/docs/articles/other/Referral-Program.md +++ b/docs/articles/expensify-classic/getting-started/Referral-Program.md @@ -50,4 +50,4 @@ Please send a message to concierge@expensify.com with the billing owner of the c Expensify members who are opted-in for our newsletters will have received an email containing their unique referral link. -On the mobile app, go to **Settings** > **Invite a Friend** > **Share Invite Link** to retrieve your referral link. +On the mobile app, go to **Settings** > **Invite a Friend** > **Share Invite Link** to retrieve your referral link. diff --git a/docs/articles/expensify-classic/getting-started/Security.md b/docs/articles/expensify-classic/getting-started/Security.md new file mode 100644 index 000000000000..5a0036e3e161 --- /dev/null +++ b/docs/articles/expensify-classic/getting-started/Security.md @@ -0,0 +1,5 @@ +--- +title: Security +description: Security +--- +## Resource Coming Soon! diff --git a/docs/articles/other/Card-Revenue-Share-for-ExpensifyApproved!-Partners.md b/docs/articles/expensify-classic/getting-started/approved-accountants/Card-Revenue-Share-For-Expensify-Approved-Partners.md similarity index 99% rename from docs/articles/other/Card-Revenue-Share-for-ExpensifyApproved!-Partners.md rename to docs/articles/expensify-classic/getting-started/approved-accountants/Card-Revenue-Share-For-Expensify-Approved-Partners.md index 44614d506d49..b18531d43200 100644 --- a/docs/articles/other/Card-Revenue-Share-for-ExpensifyApproved!-Partners.md +++ b/docs/articles/expensify-classic/getting-started/approved-accountants/Card-Revenue-Share-For-Expensify-Approved-Partners.md @@ -13,4 +13,4 @@ To benefit from this program, all you need to do is ensure that you are listed a - What if my firm is not permitted to accept revenue share from our clients?

    We understand that different firms may have different policies. If your firm is unable to accept this revenue share, you can pass the revenue share back to your client to give them an additional 0.5% of cash back using your own internal payment tools.

    - What if my firm does not wish to participate in the program?
    -
    Please reach out to your assigned partner manager at new.expensify.com to inform them you would not like to accept the revenue share nor do you want to pass the revenue share to your clients. +
    Please reach out to your assigned partner manager at new.expensify.com to inform them you would not like to accept the revenue share nor do you want to pass the revenue share to your clients. \ No newline at end of file diff --git a/docs/articles/other/Your-Expensify-Partner-Manager.md b/docs/articles/expensify-classic/getting-started/approved-accountants/Your-Expensify-Partner-Manager.md similarity index 99% rename from docs/articles/other/Your-Expensify-Partner-Manager.md rename to docs/articles/expensify-classic/getting-started/approved-accountants/Your-Expensify-Partner-Manager.md index 9a68fbfd8b39..c7a5dc5a04ab 100644 --- a/docs/articles/other/Your-Expensify-Partner-Manager.md +++ b/docs/articles/expensify-classic/getting-started/approved-accountants/Your-Expensify-Partner-Manager.md @@ -31,4 +31,4 @@ If you’re unable to contact your Partner Manager (i.e., they're out of office ## Can I get on a call with my Partner Manager? Of course! You can ask your Partner Manager to schedule a call whenever you think one might be helpful. Partner Managers can discuss client onboarding strategies, firm wide training, and client setups. -We recommend continuing to work with Concierge for **general support questions**, as this team is always online and available to help immediately. +We recommend continuing to work with Concierge for **general support questions**, as this team is always online and available to help immediately. \ No newline at end of file diff --git a/docs/articles/playbooks/Expensify-Playbook-for-Small-to-Medium-Sized-Businesses.md b/docs/articles/expensify-classic/getting-started/playbooks/Expensify-Playbook-For-Small-To-Medium-Sized-Businesses.md similarity index 99% rename from docs/articles/playbooks/Expensify-Playbook-for-Small-to-Medium-Sized-Businesses.md rename to docs/articles/expensify-classic/getting-started/playbooks/Expensify-Playbook-For-Small-To-Medium-Sized-Businesses.md index a4004dbe1b88..2b95a1d13fde 100644 --- a/docs/articles/playbooks/Expensify-Playbook-for-Small-to-Medium-Sized-Businesses.md +++ b/docs/articles/expensify-classic/getting-started/playbooks/Expensify-Playbook-For-Small-To-Medium-Sized-Businesses.md @@ -280,4 +280,4 @@ Now that we’ve gone through all of the steps for setting up your account, let 4. Click *Accept Terms* ## You’re all set! -Congrats, you are all set up! If you need any assistance with anything mentioned above or would like to understand other features available in Expensify, reach out to your Setup Specialist directly in *[new.expensify.com](https://new.expensify.com)*. Don’t have one yet? Create a Control Policy, and we’ll automatically assign a dedicated Setup Specialist to you. +Congrats, you are all set up! If you need any assistance with anything mentioned above or would like to understand other features available in Expensify, reach out to your Setup Specialist directly in *[new.expensify.com](https://new.expensify.com)*. Don’t have one yet? Create a Control Policy, and we’ll automatically assign a dedicated Setup Specialist to you. diff --git a/docs/articles/playbooks/Expensify-Playbook-for-US-Based-Bootstrapped-Startups.md b/docs/articles/expensify-classic/getting-started/playbooks/Expensify-Playbook-For-US-Based-Bootstrapped-Startups.md similarity index 99% rename from docs/articles/playbooks/Expensify-Playbook-for-US-Based-Bootstrapped-Startups.md rename to docs/articles/expensify-classic/getting-started/playbooks/Expensify-Playbook-For-US-Based-Bootstrapped-Startups.md index 089ad16834ac..86c6a583c758 100644 --- a/docs/articles/playbooks/Expensify-Playbook-for-US-Based-Bootstrapped-Startups.md +++ b/docs/articles/expensify-classic/getting-started/playbooks/Expensify-Playbook-For-US-Based-Bootstrapped-Startups.md @@ -88,4 +88,3 @@ When you have bills to pay you can click *View all bills* under the *Manage your # You’re all set! Congrats, you are all set up! If you need any assistance with anything mentioned above, reach out to either your Concierge directly in *[new.expensify.com](https://new.expensify.com/concierge)*, or email concierge@expensify.com. Create a Collect or Control Policy, and we’ll automatically assign a dedicated Setup Specialist to you. - diff --git a/docs/articles/playbooks/Expensify-Playbook-for-US-based-VC-Backed-Startups.md b/docs/articles/expensify-classic/getting-started/playbooks/Expensify-Playbook-For-US-Based-VC-Backed-Startups.md similarity index 100% rename from docs/articles/playbooks/Expensify-Playbook-for-US-based-VC-Backed-Startups.md rename to docs/articles/expensify-classic/getting-started/playbooks/Expensify-Playbook-For-US-Based-VC-Backed-Startups.md diff --git a/docs/articles/other/Your-Expensify-Account-Manager.md b/docs/articles/expensify-classic/getting-started/support/Your-Expensify-Account-Manager.md similarity index 99% rename from docs/articles/other/Your-Expensify-Account-Manager.md rename to docs/articles/expensify-classic/getting-started/support/Your-Expensify-Account-Manager.md index 70e0435e00e1..3ef47337a74c 100644 --- a/docs/articles/other/Your-Expensify-Account-Manager.md +++ b/docs/articles/expensify-classic/getting-started/support/Your-Expensify-Account-Manager.md @@ -33,4 +33,4 @@ You will be able to see if they are online via their status, which will either s If for some reason, you’re unable to reach your account manager, perhaps because they’re offline, then you can always reach out to Concierge for assistance. Your account manager will always get back to you when they’re online again. ## Can I get on a call with my account manager? -Of course! You can ask your account manager to schedule a call whenever you think one might be helpful. We usually find that the most effective calls are those that deal with general setup questions. For technical troubleshooting, we typically recommend chat as that allows your account manager time to look into the issue, test things on their end, and, if needed, consult the wider Expensify technical team. It also allows you to easily refer back to instructions and links. +Of course! You can ask your account manager to schedule a call whenever you think one might be helpful. We usually find that the most effective calls are those that deal with general setup questions. For technical troubleshooting, we typically recommend chat as that allows your account manager time to look into the issue, test things on their end, and, if needed, consult the wider Expensify technical team. It also allows you to easily refer back to instructions and links. \ No newline at end of file diff --git a/docs/articles/other/Enable-Location-Access-on-Web.md b/docs/articles/expensify-classic/getting-started/tips-and-tricks/Enable-Location-Access-On-Web.md similarity index 99% rename from docs/articles/other/Enable-Location-Access-on-Web.md rename to docs/articles/expensify-classic/getting-started/tips-and-tricks/Enable-Location-Access-On-Web.md index 6cc0d19e4cde..649212b00f7b 100644 --- a/docs/articles/other/Enable-Location-Access-on-Web.md +++ b/docs/articles/expensify-classic/getting-started/tips-and-tricks/Enable-Location-Access-On-Web.md @@ -52,4 +52,4 @@ Ask: The site must ask if it can use your location. Deny: The site can’t use your location. Allow: The site can always use your location. -[Safari help page](https://support.apple.com/guide/safari/websites-ibrwe2159f50/mac) +[Safari help page](https://support.apple.com/guide/safari/websites-ibrwe2159f50/mac) \ No newline at end of file diff --git a/docs/articles/expensify-classic/integrations/HR-integrations/ADP.md b/docs/articles/expensify-classic/integrations/HR-integrations/ADP.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/HR-integrations/ADP.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/HR-integrations/Greenhouse.md b/docs/articles/expensify-classic/integrations/HR-integrations/Greenhouse.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/HR-integrations/Greenhouse.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/HR-integrations/Gusto.md b/docs/articles/expensify-classic/integrations/HR-integrations/Gusto.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/HR-integrations/Gusto.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/HR-integrations/QuickBooks-Time.md b/docs/articles/expensify-classic/integrations/HR-integrations/QuickBooks-Time.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/HR-integrations/QuickBooks-Time.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/HR-integrations/Rippling.md b/docs/articles/expensify-classic/integrations/HR-integrations/Rippling.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/HR-integrations/Rippling.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/HR-integrations/Workday.md b/docs/articles/expensify-classic/integrations/HR-integrations/Workday.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/HR-integrations/Workday.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/HR-integrations/Zenefits.md b/docs/articles/expensify-classic/integrations/HR-integrations/Zenefits.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/HR-integrations/Zenefits.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/accounting-integrations/FinancalForce.md b/docs/articles/expensify-classic/integrations/accounting-integrations/FinancalForce.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/accounting-integrations/FinancalForce.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/accounting-integrations/NetSuite.md b/docs/articles/expensify-classic/integrations/accounting-integrations/NetSuite.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/accounting-integrations/NetSuite.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/accounting-integrations/QuickBooks-Desktop.md b/docs/articles/expensify-classic/integrations/accounting-integrations/QuickBooks-Desktop.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/accounting-integrations/QuickBooks-Desktop.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/accounting-integrations/QuickBooks-Online.md b/docs/articles/expensify-classic/integrations/accounting-integrations/QuickBooks-Online.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/accounting-integrations/QuickBooks-Online.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/accounting-integrations/Sage-Intacct.md b/docs/articles/expensify-classic/integrations/accounting-integrations/Sage-Intacct.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/accounting-integrations/Sage-Intacct.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/accounting-integrations/Xero.md b/docs/articles/expensify-classic/integrations/accounting-integrations/Xero.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/accounting-integrations/Xero.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/other-integrations/Google-Apps-SSO.md b/docs/articles/expensify-classic/integrations/other-integrations/Google-Apps-SSO.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/other-integrations/Google-Apps-SSO.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/travel-integrations/Bolt.md b/docs/articles/expensify-classic/integrations/travel-integrations/Bolt.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/travel-integrations/Bolt.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/travel-integrations/Egencia.md b/docs/articles/expensify-classic/integrations/travel-integrations/Egencia.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/travel-integrations/Egencia.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/travel-integrations/Global-VaTax.md b/docs/articles/expensify-classic/integrations/travel-integrations/Global-VaTax.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/travel-integrations/Global-VaTax.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/travel-integrations/Grab.md b/docs/articles/expensify-classic/integrations/travel-integrations/Grab.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/travel-integrations/Grab.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/travel-integrations/Hotel-Tonight.md b/docs/articles/expensify-classic/integrations/travel-integrations/Hotel-Tonight.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/travel-integrations/Hotel-Tonight.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/travel-integrations/Kayak.md b/docs/articles/expensify-classic/integrations/travel-integrations/Kayak.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/travel-integrations/Kayak.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/travel-integrations/Lyft.md b/docs/articles/expensify-classic/integrations/travel-integrations/Lyft.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/travel-integrations/Lyft.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/travel-integrations/TrainLine.md b/docs/articles/expensify-classic/integrations/travel-integrations/TrainLine.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/travel-integrations/TrainLine.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/travel-integrations/TravelPerk.md b/docs/articles/expensify-classic/integrations/travel-integrations/TravelPerk.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/travel-integrations/TravelPerk.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/travel-integrations/Trip-Actions.md b/docs/articles/expensify-classic/integrations/travel-integrations/Trip-Actions.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/travel-integrations/Trip-Actions.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/travel-integrations/TripCatcher.md b/docs/articles/expensify-classic/integrations/travel-integrations/TripCatcher.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/travel-integrations/TripCatcher.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/integrations/travel-integrations/Uber.md b/docs/articles/expensify-classic/integrations/travel-integrations/Uber.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/integrations/travel-integrations/Uber.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/manage-employees-and-report-approvals/Adding-Users.md b/docs/articles/expensify-classic/manage-employees-and-report-approvals/Adding-Users.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/manage-employees-and-report-approvals/Adding-Users.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/manage-employees-and-report-approvals/Approval-Workflows.md b/docs/articles/expensify-classic/manage-employees-and-report-approvals/Approval-Workflows.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/manage-employees-and-report-approvals/Approval-Workflows.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/manage-employees-and-report-approvals/Approving-Reports.md b/docs/articles/expensify-classic/manage-employees-and-report-approvals/Approving-Reports.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/manage-employees-and-report-approvals/Approving-Reports.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/manage-employees-and-report-approvals/User-Roles.md b/docs/articles/expensify-classic/manage-employees-and-report-approvals/User-Roles.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/manage-employees-and-report-approvals/User-Roles.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/manage-employees-and-report-approvals/Vacation-Delegate.md b/docs/articles/expensify-classic/manage-employees-and-report-approvals/Vacation-Delegate.md new file mode 100644 index 000000000000..e107734216f5 --- /dev/null +++ b/docs/articles/expensify-classic/manage-employees-and-report-approvals/Vacation-Delegate.md @@ -0,0 +1,8 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! + + +Kayak.md Lyft.md TrainLine.md TravelPerk.md Trip Actions.md TripCatcher.md Uber.md \ No newline at end of file diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Admins.md b/docs/articles/expensify-classic/policy-and-domain-settings/Admins.md new file mode 100644 index 000000000000..cea96cfe2057 --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Admins.md @@ -0,0 +1,5 @@ +--- +title: Admins +description: Admins +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Categories.md b/docs/articles/expensify-classic/policy-and-domain-settings/Categories.md new file mode 100644 index 000000000000..0db022f400d3 --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Categories.md @@ -0,0 +1,5 @@ +--- +title: Categories +description: Categories +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Domain-Admins.md b/docs/articles/expensify-classic/policy-and-domain-settings/Domain-Admins.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Domain-Admins.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Domain-Members.md b/docs/articles/expensify-classic/policy-and-domain-settings/Domain-Members.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Domain-Members.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Domains-Overview.md b/docs/articles/expensify-classic/policy-and-domain-settings/Domains-Overview.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Domains-Overview.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Expenses.md b/docs/articles/expensify-classic/policy-and-domain-settings/Expenses.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Expenses.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Invoicing.md b/docs/articles/expensify-classic/policy-and-domain-settings/Invoicing.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Invoicing.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Overview.md b/docs/articles/expensify-classic/policy-and-domain-settings/Overview.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Overview.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Per-Diem.md b/docs/articles/expensify-classic/policy-and-domain-settings/Per-Diem.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Per-Diem.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Reimbursement.md b/docs/articles/expensify-classic/policy-and-domain-settings/Reimbursement.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Reimbursement.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Reports.md b/docs/articles/expensify-classic/policy-and-domain-settings/Reports.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Reports.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/SAML.md b/docs/articles/expensify-classic/policy-and-domain-settings/SAML.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/SAML.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Tags.md b/docs/articles/expensify-classic/policy-and-domain-settings/Tags.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Tags.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Tax.md b/docs/articles/expensify-classic/policy-and-domain-settings/Tax.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Tax.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/policy-and-domain-settings/Trips.md b/docs/articles/expensify-classic/policy-and-domain-settings/Trips.md new file mode 100644 index 000000000000..3ee1c8656b4b --- /dev/null +++ b/docs/articles/expensify-classic/policy-and-domain-settings/Trips.md @@ -0,0 +1,5 @@ +--- +title: Coming Soon +description: Coming Soon +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/send-payments/Pay-Bills.md b/docs/articles/expensify-classic/send-payments/Pay-Bills.md new file mode 100644 index 000000000000..41c0146126ba --- /dev/null +++ b/docs/articles/expensify-classic/send-payments/Pay-Bills.md @@ -0,0 +1,5 @@ +--- +title: Pay Bills +description: Pay Bills +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/send-payments/Pay-Invoices.md b/docs/articles/expensify-classic/send-payments/Pay-Invoices.md new file mode 100644 index 000000000000..e5e6799c268c --- /dev/null +++ b/docs/articles/expensify-classic/send-payments/Pay-Invoices.md @@ -0,0 +1,5 @@ +--- +title: Pay Invoices +description: Pay Invoices +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/send-payments/Reimbursing-Reports.md b/docs/articles/expensify-classic/send-payments/Reimbursing-Reports.md new file mode 100644 index 000000000000..834d0b159931 --- /dev/null +++ b/docs/articles/expensify-classic/send-payments/Reimbursing-Reports.md @@ -0,0 +1,5 @@ +--- +title: Reimbursing Reports +description: Reimbursing Reports +--- +## Resource Coming Soon! diff --git a/docs/articles/expensify-classic/send-payments/Third-Party-Payments.md b/docs/articles/expensify-classic/send-payments/Third-Party-Payments.md new file mode 100644 index 000000000000..f61f26d91059 --- /dev/null +++ b/docs/articles/expensify-classic/send-payments/Third-Party-Payments.md @@ -0,0 +1,8 @@ +--- +title: Third Party Payments +description: Third Party Payments +--- +## Resource Coming Soon! + + + \ No newline at end of file diff --git a/docs/articles/new-expensify/account-settings/Coming-Soon.md b/docs/articles/new-expensify/account-settings/Coming-Soon.md new file mode 100644 index 000000000000..6b85bb0364b5 --- /dev/null +++ b/docs/articles/new-expensify/account-settings/Coming-Soon.md @@ -0,0 +1,4 @@ +--- +title: Coming Soon +description: Coming Soon +--- diff --git a/docs/articles/new-expensify/bank-accounts-and-credit-cards/Coming-Soon.md b/docs/articles/new-expensify/bank-accounts-and-credit-cards/Coming-Soon.md new file mode 100644 index 000000000000..6b85bb0364b5 --- /dev/null +++ b/docs/articles/new-expensify/bank-accounts-and-credit-cards/Coming-Soon.md @@ -0,0 +1,4 @@ +--- +title: Coming Soon +description: Coming Soon +--- diff --git a/docs/articles/split-bills/workspaces/The-Free-Plan.md b/docs/articles/new-expensify/billing-and-plan-types/The-Free-Plan.md similarity index 98% rename from docs/articles/split-bills/workspaces/The-Free-Plan.md rename to docs/articles/new-expensify/billing-and-plan-types/The-Free-Plan.md index 45c9d09d4777..0a8d6b3493e0 100644 --- a/docs/articles/split-bills/workspaces/The-Free-Plan.md +++ b/docs/articles/new-expensify/billing-and-plan-types/The-Free-Plan.md @@ -59,4 +59,4 @@ Categories are standardized on the Free Plan and can’t be edited. Custom categ ## With the Free Plan, can I export reports using a custom format? -The Free Plan offers standard report export formats. You'll need to upgrade to a paid plan to create a custom export format. +The Free Plan offers standard report export formats. You'll need to upgrade to a paid plan to create a custom export format. \ No newline at end of file diff --git a/docs/articles/new-expensify/expense-and-report-features/Coming-Soon.md b/docs/articles/new-expensify/expense-and-report-features/Coming-Soon.md new file mode 100644 index 000000000000..6b85bb0364b5 --- /dev/null +++ b/docs/articles/new-expensify/expense-and-report-features/Coming-Soon.md @@ -0,0 +1,4 @@ +--- +title: Coming Soon +description: Coming Soon +--- diff --git a/docs/articles/new-expensify/expensify-card/Coming-Soon.md b/docs/articles/new-expensify/expensify-card/Coming-Soon.md new file mode 100644 index 000000000000..6b85bb0364b5 --- /dev/null +++ b/docs/articles/new-expensify/expensify-card/Coming-Soon.md @@ -0,0 +1,4 @@ +--- +title: Coming Soon +description: Coming Soon +--- diff --git a/docs/articles/new-expensify/exports/Coming-Soon.md b/docs/articles/new-expensify/exports/Coming-Soon.md new file mode 100644 index 000000000000..6b85bb0364b5 --- /dev/null +++ b/docs/articles/new-expensify/exports/Coming-Soon.md @@ -0,0 +1,4 @@ +--- +title: Coming Soon +description: Coming Soon +--- diff --git a/docs/articles/new-expensify/get-paid-back/Request-Money.md b/docs/articles/new-expensify/get-paid-back/Request-Money.md new file mode 100644 index 000000000000..dc6de6656cc9 --- /dev/null +++ b/docs/articles/new-expensify/get-paid-back/Request-Money.md @@ -0,0 +1,5 @@ +--- +title: Request Money +description: Request Money +--- +## Resource Coming Soon! diff --git a/docs/articles/other/Expensify-Lounge.md b/docs/articles/new-expensify/getting-started/Expensify-Lounge.md similarity index 100% rename from docs/articles/other/Expensify-Lounge.md rename to docs/articles/new-expensify/getting-started/Expensify-Lounge.md diff --git a/docs/articles/new-expensify/getting-started/Referral-Program.md b/docs/articles/new-expensify/getting-started/Referral-Program.md new file mode 100644 index 000000000000..683e93d0277a --- /dev/null +++ b/docs/articles/new-expensify/getting-started/Referral-Program.md @@ -0,0 +1,53 @@ +--- +title: Expensify Referral Program +description: Send your joining link, submit a receipt or invoice, and we'll pay you if your referral adopts Expensify. +--- + + +# About + +Expensify has grown thanks to our users who love Expensify so much that they tell their friends, colleagues, managers, and fellow business founders to use it, too. + +As a thank you, every time you bring a new user into the platform who directly or indirectly leads to the adoption of a paid annual plan on Expensify, you will earn $250. + +# How to get paid for referring people to Expensify + +1. Submit a report or invoice, or share your referral link with anyone you know who is spending too much time on expenses, or works at a company that could benefit from using Expensify. + +2. You will get $250 for any referred business that commits to an annual subscription, has 2 or more active users, and makes two monthly payments. + +That’s right! You can refer anyone working at any company you know. + +If their company goes on to become an Expensify customer with an annual subscription, and you are the earliest recorded referrer of a user on that company’s paid Expensify Policy, you'll get paid a referral reward. + +The best way to start is to submit any receipt to your manager (you'll get paid back and set yourself up for $250 if they start a subscription: win-win!) + +Referral rewards for the Spring/Summer 2023 campaign will be paid by direct deposit. + +# FAQ + +- **How will I know if I am the first person to refer a company to Expensify?** + +Successful referrers are notified after their referral pays for 2 months of an annual subscription. We will check for the earliest recorded referrer of a user on the policy, and if that is you, then we will let you know. + +- **How will you pay me if I am successful?** + +In the Spring 2023 campaign, Expensify will be paying successful referrers via direct deposit to the Deposit-Only account you have on file. Referral payouts will happen once a month for the duration of the campaign. If you do not have a Deposit-Only account at the time of your referral payout, your deposit will be processed in the next batch. + +Learn how to add a Deposit-Only account [here](https://community.expensify.com/discussion/4641/how-to-add-a-deposit-only-bank-account-both-personal-and-business). + +- **I’m outside of the US, how do I get paid?** + +While our referral payouts are in USD, you will be able to get paid via a Wise Borderless account. Learn more [here](https://community.expensify.com/discussion/5940/how-to-get-reimbursed-outside-the-us-with-wise-for-non-us-employees). + +- **My referral wasn’t counted! How can I appeal?** + +Expensify reserves the right to modify the terms of the referral program at any time, and pays out referral bonuses for eligible companies at its own discretion. + +Please send a message to concierge@expensify.com with the billing owner of the company you have referred and our team will review the referral and get back to you. + +- **Where can I find my referral link?** + +Expensify members who are opted-in for our newsletters will have received an email containing their unique referral link. + +On the mobile app, go to **Settings** > **Invite a Friend** > **Share Invite Link** to retrieve your referral link. diff --git a/docs/articles/other/Everything-About-Chat.md b/docs/articles/new-expensify/getting-started/chat/Everything-About-Chat.md similarity index 99% rename from docs/articles/other/Everything-About-Chat.md rename to docs/articles/new-expensify/getting-started/chat/Everything-About-Chat.md index d52932daa5ff..9f73d1c759c2 100644 --- a/docs/articles/other/Everything-About-Chat.md +++ b/docs/articles/new-expensify/getting-started/chat/Everything-About-Chat.md @@ -83,5 +83,3 @@ You will receive a whisper from Concierge any time your content has been flagged ![Moderation Reporter Whisper](https://help.expensify.com/assets/images/moderation-reporter-whisper.png){:width="100%"} *Note: Any message sent in public chat rooms are automatically reviewed by an automated system looking for offensive content and sent to our moderators for final decisions if it is found.* - - diff --git a/docs/articles/other/Expensify-Chat-For-Admins.md b/docs/articles/new-expensify/getting-started/chat/Expensify-Chat-For-Admins.md similarity index 99% rename from docs/articles/other/Expensify-Chat-For-Admins.md rename to docs/articles/new-expensify/getting-started/chat/Expensify-Chat-For-Admins.md index 247b2b0e03d0..31de150d5b5e 100644 --- a/docs/articles/other/Expensify-Chat-For-Admins.md +++ b/docs/articles/new-expensify/getting-started/chat/Expensify-Chat-For-Admins.md @@ -24,3 +24,4 @@ In order to get the most out of Expensify Chat, we created a list of best practi - The rooms will all stay open after the conference ends, so encourage speakers to keep engaging as long as the conversation is going in their session room. - Continue sharing photos and videos from the event or anything fun in #social as part of a wrap up for everyone. - Use the #announce room to give attendees a sneak preview of your next event. +- \ No newline at end of file diff --git a/docs/articles/other/Expensify-Chat-For-Conference-Attendees.md b/docs/articles/new-expensify/getting-started/chat/Expensify-Chat-For-Conference-Attendees.md similarity index 100% rename from docs/articles/other/Expensify-Chat-For-Conference-Attendees.md rename to docs/articles/new-expensify/getting-started/chat/Expensify-Chat-For-Conference-Attendees.md diff --git a/docs/articles/other/Expensify-Chat-For-Conference-Speakers.md b/docs/articles/new-expensify/getting-started/chat/Expensify-Chat-For-Conference-Speakers.md similarity index 100% rename from docs/articles/other/Expensify-Chat-For-Conference-Speakers.md rename to docs/articles/new-expensify/getting-started/chat/Expensify-Chat-For-Conference-Speakers.md diff --git a/docs/articles/playbooks/Expensify-Chat-Playbook-for-Conferences.md b/docs/articles/new-expensify/getting-started/chat/Expensify-Chat-Playbook-For-Conferences.md similarity index 100% rename from docs/articles/playbooks/Expensify-Chat-Playbook-for-Conferences.md rename to docs/articles/new-expensify/getting-started/chat/Expensify-Chat-Playbook-For-Conferences.md diff --git a/docs/articles/new-expensify/integrations/accounting-integrations/QuickBooks-Online.md b/docs/articles/new-expensify/integrations/accounting-integrations/QuickBooks-Online.md new file mode 100644 index 000000000000..aa5f40ee4e5d --- /dev/null +++ b/docs/articles/new-expensify/integrations/accounting-integrations/QuickBooks-Online.md @@ -0,0 +1,5 @@ +--- +title: QuickBooks Online +description: QuickBooks Online +--- +## Resource Coming Soon! diff --git a/docs/articles/new-expensify/manage-employees-and-report-approvals/Coming-Soon.md b/docs/articles/new-expensify/manage-employees-and-report-approvals/Coming-Soon.md new file mode 100644 index 000000000000..6b85bb0364b5 --- /dev/null +++ b/docs/articles/new-expensify/manage-employees-and-report-approvals/Coming-Soon.md @@ -0,0 +1,4 @@ +--- +title: Coming Soon +description: Coming Soon +--- diff --git a/docs/articles/new-expensify/send-payments/Coming-Soon.md b/docs/articles/new-expensify/send-payments/Coming-Soon.md new file mode 100644 index 000000000000..6b85bb0364b5 --- /dev/null +++ b/docs/articles/new-expensify/send-payments/Coming-Soon.md @@ -0,0 +1,4 @@ +--- +title: Coming Soon +description: Coming Soon +--- diff --git a/docs/articles/new-expensify/workspace-and-domain-settings/Coming-Soon.md b/docs/articles/new-expensify/workspace-and-domain-settings/Coming-Soon.md new file mode 100644 index 000000000000..6b85bb0364b5 --- /dev/null +++ b/docs/articles/new-expensify/workspace-and-domain-settings/Coming-Soon.md @@ -0,0 +1,4 @@ +--- +title: Coming Soon +description: Coming Soon +--- diff --git a/docs/articles/request-money/Request-and-Split-Bills.md b/docs/articles/request-money/Request-and-Split-Bills.md deleted file mode 100644 index bb27cd75c742..000000000000 --- a/docs/articles/request-money/Request-and-Split-Bills.md +++ /dev/null @@ -1,38 +0,0 @@ ---- -title: Request Money and Split Bills with Friends -description: Everything you need to know about Requesting Money and Splitting Bills with Friends! ---- - - - -# How do these Payment Features work? -Our suite of money movement features enables you to request money owed by an individual or split a bill with a group. - -**Request Money** lets your friends pay you back directly in Expensify. When you send a payment request to a friend, Expensify will display the amount owed and the option to pay the corresponding request in a chat between you. - -**Split Bill** allows you to split payments between friends and ensures the person who settled the tab gets paid back. - -These two features ensure you can live in the moment and settle up afterward. - -# How to Request Money -- Select the Green **+** button and choose **Request Money** -- Select the relevant option: - - **Manual:** Enter the merchant and amount manually. - - **Scan:** Take a photo of the receipt to have the merchant and amount auto-filled. - - **Distance:** Enter the details of your trip, plus any stops along the way, and the mileage and amount will be automatically calculated. -- Search for the user or enter their email! -- Enter a reason for the request (optional) -- Click **Request!** -- If you change your mind, all you have to do is click **Cancel** -- The user will be able to **Settle up outside of Expensify** or pay you via **Venmo** or **PayPal.me** - -# How to Split a Bill -- Select the Green **+** button and choose **Split Bill** -- Enter the total amount for the bill and click **Next** -- Search for users or enter their emails and **Select** -- Enter a reason for the split -- The split is then shared equally between the attendees - -# FAQs -## Can I request money from more than one person at a time? -If you need to request money for more than one person at a time, you’ll want to use the Split Bill feature. The Request Money option is for one-to-one payments between two people. diff --git a/docs/articles/split-bills/paying-friends/Request-and-Split-Bills.md b/docs/articles/split-bills/paying-friends/Request-and-Split-Bills.md deleted file mode 100644 index a2c63cf6f8f7..000000000000 --- a/docs/articles/split-bills/paying-friends/Request-and-Split-Bills.md +++ /dev/null @@ -1,35 +0,0 @@ ---- -title: Request Money and Split Bills with Friends -description: Everything you need to know about Requesting Money and Splitting Bills with Friends! ---- - - - -# How do these Payment Features work? -Our suite of money movement features enables you to request money owed by an individual or split a bill with a group. - -**Request Money** lets your friends pay you back directly in Expensify. When you send a payment request to a friend, Expensify will display the amount owed and the option to pay the corresponding request in a chat between you. - -**Split Bill** allows you to split payments between friends and ensures the person who settled the tab gets paid back. - -These two features ensure you can live in the moment and settle up afterward. - -# How to Request Money -- Select the Green **+** button and choose **Request Money** -- Enter the amount **$** they owe and click **Next** -- Search for the user or enter their email! -- Enter a reason for the request (optional) -- Click **Request!** -- If you change your mind, all you have to do is click **Cancel** -- The user will be able to **Settle up outside of Expensify** or pay you via **Venmo** or **PayPal.me** - -# How to Split a Bill -- Select the Green **+** button and choose **Split Bill** -- Enter the total amount for the bill and click **Next** -- Search for users or enter their emails and **Select** -- Enter a reason for the split -- The split is then shared equally between the attendees - -# FAQs -## Can I request money from more than one person at a time? -If you need to request money for more than one person at a time, you’ll want to use the Split Bill feature. The Request Money option is for one-to-one payments between two people. diff --git a/docs/assets/images/accounting.svg b/docs/assets/images/accounting.svg new file mode 100644 index 000000000000..4398e9573747 --- /dev/null +++ b/docs/assets/images/accounting.svg @@ -0,0 +1,68 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/assets/images/bank-card.svg b/docs/assets/images/bank-card.svg new file mode 100644 index 000000000000..48da9af0d986 --- /dev/null +++ b/docs/assets/images/bank-card.svg @@ -0,0 +1,41 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/assets/images/envelope-receipt.svg b/docs/assets/images/envelope-receipt.svg new file mode 100644 index 000000000000..40f57cc4ebda --- /dev/null +++ b/docs/assets/images/envelope-receipt.svg @@ -0,0 +1,35 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/assets/images/gears.svg b/docs/assets/images/gears.svg new file mode 100644 index 000000000000..23621afc8008 --- /dev/null +++ b/docs/assets/images/gears.svg @@ -0,0 +1,101 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/assets/images/hand-card.svg b/docs/assets/images/hand-card.svg new file mode 100644 index 000000000000..779e6ff4184c --- /dev/null +++ b/docs/assets/images/hand-card.svg @@ -0,0 +1,19 @@ + + + + + + + + + + + + + + + + + + + diff --git a/docs/assets/images/money-into-wallet.svg b/docs/assets/images/money-into-wallet.svg new file mode 100644 index 000000000000..d6d5b0e7d6e7 --- /dev/null +++ b/docs/assets/images/money-into-wallet.svg @@ -0,0 +1,32 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/assets/images/money-receipt.svg b/docs/assets/images/money-receipt.svg new file mode 100644 index 000000000000..379d56727e42 --- /dev/null +++ b/docs/assets/images/money-receipt.svg @@ -0,0 +1,34 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/assets/images/money-wings.svg b/docs/assets/images/money-wings.svg new file mode 100644 index 000000000000..c2155080f721 --- /dev/null +++ b/docs/assets/images/money-wings.svg @@ -0,0 +1,26 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/assets/images/monitor.svg b/docs/assets/images/monitor.svg new file mode 100644 index 000000000000..6e2580b4c9e8 --- /dev/null +++ b/docs/assets/images/monitor.svg @@ -0,0 +1,12 @@ + + + + + + + + + + + + diff --git a/docs/assets/images/settings-new-dot.svg b/docs/assets/images/settings-new-dot.svg new file mode 100644 index 000000000000..13338fc72362 --- /dev/null +++ b/docs/assets/images/settings-new-dot.svg @@ -0,0 +1,88 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/assets/images/settings-old-dot.svg b/docs/assets/images/settings-old-dot.svg new file mode 100644 index 000000000000..89302b65c70d --- /dev/null +++ b/docs/assets/images/settings-old-dot.svg @@ -0,0 +1,187 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/assets/images/shield.svg b/docs/assets/images/shield.svg index 9066e116c94c..252da0321692 100644 --- a/docs/assets/images/shield.svg +++ b/docs/assets/images/shield.svg @@ -1,4 +1,16 @@ - - - + + + + + + + + + + + + + + + diff --git a/docs/assets/images/workflow.svg b/docs/assets/images/workflow.svg new file mode 100644 index 000000000000..e5eac423cd1d --- /dev/null +++ b/docs/assets/images/workflow.svg @@ -0,0 +1,117 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/docs/assets/js/main.js b/docs/assets/js/main.js index f0f335536c20..aebd0f5d4864 100644 --- a/docs/assets/js/main.js +++ b/docs/assets/js/main.js @@ -58,10 +58,10 @@ function navigateBack() { return; } - const hubs = JSON.parse(document.getElementById('hubs-data').value); - const hubToNavigate = hubs.find((hub) => window.location.pathname.includes(hub)); // eslint-disable-line rulesdir/prefer-underscore-method - if (hubToNavigate) { - window.location.href = `/hubs/${hubToNavigate}`; + // Path name is of the form /articles/[platform]/[hub]/[resource] + const path = window.location.pathname.split('/'); + if (path[2] && path[3]) { + window.location.href = `/${path[2]}/hubs/${path[3]}`; } else { window.location.href = '/'; } diff --git a/docs/expensify-classic/hubs/account-settings/index.html b/docs/expensify-classic/hubs/account-settings/index.html new file mode 100644 index 000000000000..434761a6c4fa --- /dev/null +++ b/docs/expensify-classic/hubs/account-settings/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Account Settings +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/expensify-classic/hubs/bank-accounts-and-credit-cards/business-bank-accounts.html b/docs/expensify-classic/hubs/bank-accounts-and-credit-cards/business-bank-accounts.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/bank-accounts-and-credit-cards/business-bank-accounts.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/bank-accounts-and-credit-cards/company-cards.html b/docs/expensify-classic/hubs/bank-accounts-and-credit-cards/company-cards.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/bank-accounts-and-credit-cards/company-cards.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/bank-accounts-and-credit-cards/deposit-accounts.html b/docs/expensify-classic/hubs/bank-accounts-and-credit-cards/deposit-accounts.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/bank-accounts-and-credit-cards/deposit-accounts.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/bank-accounts-and-credit-cards/index.html b/docs/expensify-classic/hubs/bank-accounts-and-credit-cards/index.html new file mode 100644 index 000000000000..2f91f0913d6e --- /dev/null +++ b/docs/expensify-classic/hubs/bank-accounts-and-credit-cards/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Bank Accounts & Credit Cards +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/expensify-classic/hubs/billing-and-subscriptions/index.html b/docs/expensify-classic/hubs/billing-and-subscriptions/index.html new file mode 100644 index 000000000000..05dc38835b51 --- /dev/null +++ b/docs/expensify-classic/hubs/billing-and-subscriptions/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Billing & Subscriptions +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/expensify-classic/hubs/expense-and-report-features/index.html b/docs/expensify-classic/hubs/expense-and-report-features/index.html new file mode 100644 index 000000000000..44afa4b18b51 --- /dev/null +++ b/docs/expensify-classic/hubs/expense-and-report-features/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Expense & Report Settings +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/expensify-classic/hubs/expensify-card/index.html b/docs/expensify-classic/hubs/expensify-card/index.html new file mode 100644 index 000000000000..3afd8ac662e7 --- /dev/null +++ b/docs/expensify-classic/hubs/expensify-card/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Expensify Card +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/expensify-classic/hubs/exports/index.html b/docs/expensify-classic/hubs/exports/index.html new file mode 100644 index 000000000000..16c96cb51d01 --- /dev/null +++ b/docs/expensify-classic/hubs/exports/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Exports +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/expensify-classic/hubs/get-paid-back/expenses.html b/docs/expensify-classic/hubs/get-paid-back/expenses.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/get-paid-back/expenses.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/get-paid-back/index.html b/docs/expensify-classic/hubs/get-paid-back/index.html new file mode 100644 index 000000000000..1f84c1510b92 --- /dev/null +++ b/docs/expensify-classic/hubs/get-paid-back/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Get Paid Back +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/expensify-classic/hubs/get-paid-back/reports.html b/docs/expensify-classic/hubs/get-paid-back/reports.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/get-paid-back/reports.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/getting-started/approved-accountants.html b/docs/expensify-classic/hubs/getting-started/approved-accountants.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/getting-started/approved-accountants.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/getting-started/index.html b/docs/expensify-classic/hubs/getting-started/index.html new file mode 100644 index 000000000000..14ca13d0c2e8 --- /dev/null +++ b/docs/expensify-classic/hubs/getting-started/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Getting Started +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/expensify-classic/hubs/getting-started/playbooks.html b/docs/expensify-classic/hubs/getting-started/playbooks.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/getting-started/playbooks.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/getting-started/support.html b/docs/expensify-classic/hubs/getting-started/support.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/getting-started/support.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/getting-started/tips-and-tricks.html b/docs/expensify-classic/hubs/getting-started/tips-and-tricks.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/getting-started/tips-and-tricks.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/index.html b/docs/expensify-classic/hubs/index.html new file mode 100644 index 000000000000..05c7b52bfa2d --- /dev/null +++ b/docs/expensify-classic/hubs/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Expensify Classic +--- + +{% include platform.html %} \ No newline at end of file diff --git a/docs/expensify-classic/hubs/integrations/HR-integrations.html b/docs/expensify-classic/hubs/integrations/HR-integrations.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/integrations/HR-integrations.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/integrations/accounting-integrations.html b/docs/expensify-classic/hubs/integrations/accounting-integrations.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/integrations/accounting-integrations.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/integrations/index.html b/docs/expensify-classic/hubs/integrations/index.html new file mode 100644 index 000000000000..d1f173534c8a --- /dev/null +++ b/docs/expensify-classic/hubs/integrations/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Integrations +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/expensify-classic/hubs/integrations/other-integrations.html b/docs/expensify-classic/hubs/integrations/other-integrations.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/integrations/other-integrations.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/integrations/travel-integrations.html b/docs/expensify-classic/hubs/integrations/travel-integrations.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/expensify-classic/hubs/integrations/travel-integrations.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/expensify-classic/hubs/manage-employees-and-report-approvals/index.html b/docs/expensify-classic/hubs/manage-employees-and-report-approvals/index.html new file mode 100644 index 000000000000..788e445ebc91 --- /dev/null +++ b/docs/expensify-classic/hubs/manage-employees-and-report-approvals/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Manage Employees And Report Approvals +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/expensify-classic/hubs/policy-and-domain-settings/index.html b/docs/expensify-classic/hubs/policy-and-domain-settings/index.html new file mode 100644 index 000000000000..ffd514fcb6fa --- /dev/null +++ b/docs/expensify-classic/hubs/policy-and-domain-settings/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Policy And Domain Settings +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/expensify-classic/hubs/send-payments/index.html b/docs/expensify-classic/hubs/send-payments/index.html new file mode 100644 index 000000000000..c8275af5c353 --- /dev/null +++ b/docs/expensify-classic/hubs/send-payments/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Send Payments +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/hubs/other.html b/docs/hubs/other.html deleted file mode 100644 index 7d6d7f204062..000000000000 --- a/docs/hubs/other.html +++ /dev/null @@ -1,6 +0,0 @@ ---- -layout: default -title: Other ---- - -{% include hub.html %} diff --git a/docs/hubs/playbooks.html b/docs/hubs/playbooks.html deleted file mode 100644 index 0f15922fd061..000000000000 --- a/docs/hubs/playbooks.html +++ /dev/null @@ -1,6 +0,0 @@ ---- -layout: default -title: Playbooks ---- - -{% include hub.html %} diff --git a/docs/hubs/request-money.html b/docs/hubs/request-money.html deleted file mode 100644 index e3ef68f5c050..000000000000 --- a/docs/hubs/request-money.html +++ /dev/null @@ -1,6 +0,0 @@ ---- -layout: default -title: Request money ---- - -{% include hub.html %} diff --git a/docs/hubs/split-bills.html b/docs/hubs/split-bills.html deleted file mode 100644 index 6464ab62ef07..000000000000 --- a/docs/hubs/split-bills.html +++ /dev/null @@ -1,6 +0,0 @@ ---- -layout: default -title: Split bills ---- - -{% include hub.html %} diff --git a/docs/index.html b/docs/index.html index 74296c200971..70bd5f31545a 100644 --- a/docs/index.html +++ b/docs/index.html @@ -6,15 +6,11 @@

    {{ site.data.routes.home.title }}

    {{ site.data.routes.home.description }}

    -

    - Which best describes how you use Expensify? -

    -
    - {% include hub-card.html href="split-bills" %} - {% include hub-card.html href="request-money" %} - {% include hub-card.html href="playbooks" %} - {% include hub-card.html href="other" %} + {% for platform in site.data.routes.platforms %} + {% assign platform_href = platform.href %} + {% include platform-card.html href=platform.platform_href %} + {% endfor %}
    diff --git a/docs/new-expensify/hubs/account-settings/index.html b/docs/new-expensify/hubs/account-settings/index.html new file mode 100644 index 000000000000..434761a6c4fa --- /dev/null +++ b/docs/new-expensify/hubs/account-settings/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Account Settings +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/new-expensify/hubs/bank-accounts-and-credit-cards/index.html b/docs/new-expensify/hubs/bank-accounts-and-credit-cards/index.html new file mode 100644 index 000000000000..2f91f0913d6e --- /dev/null +++ b/docs/new-expensify/hubs/bank-accounts-and-credit-cards/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Bank Accounts & Credit Cards +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/new-expensify/hubs/billing-and-plan-types/index.html b/docs/new-expensify/hubs/billing-and-plan-types/index.html new file mode 100644 index 000000000000..b49b2b62b1d6 --- /dev/null +++ b/docs/new-expensify/hubs/billing-and-plan-types/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Billing & Plan Types +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/new-expensify/hubs/expense-and-report-features/index.html b/docs/new-expensify/hubs/expense-and-report-features/index.html new file mode 100644 index 000000000000..0057ae0fa46c --- /dev/null +++ b/docs/new-expensify/hubs/expense-and-report-features/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Expense and Report Features +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/new-expensify/hubs/expensify-card/index.html b/docs/new-expensify/hubs/expensify-card/index.html new file mode 100644 index 000000000000..3afd8ac662e7 --- /dev/null +++ b/docs/new-expensify/hubs/expensify-card/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Expensify Card +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/new-expensify/hubs/exports/index.html b/docs/new-expensify/hubs/exports/index.html new file mode 100644 index 000000000000..16c96cb51d01 --- /dev/null +++ b/docs/new-expensify/hubs/exports/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Exports +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/new-expensify/hubs/get-paid-back/index.html b/docs/new-expensify/hubs/get-paid-back/index.html new file mode 100644 index 000000000000..1f84c1510b92 --- /dev/null +++ b/docs/new-expensify/hubs/get-paid-back/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Get Paid Back +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/new-expensify/hubs/getting-started/chat.html b/docs/new-expensify/hubs/getting-started/chat.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/new-expensify/hubs/getting-started/chat.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/new-expensify/hubs/getting-started/index.html b/docs/new-expensify/hubs/getting-started/index.html new file mode 100644 index 000000000000..14ca13d0c2e8 --- /dev/null +++ b/docs/new-expensify/hubs/getting-started/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Getting Started +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/new-expensify/hubs/index.html b/docs/new-expensify/hubs/index.html new file mode 100644 index 000000000000..de046b16e755 --- /dev/null +++ b/docs/new-expensify/hubs/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: New Expensify +--- + +{% include platform.html %} \ No newline at end of file diff --git a/docs/new-expensify/hubs/integrations/accounting-integrations.html b/docs/new-expensify/hubs/integrations/accounting-integrations.html new file mode 100644 index 000000000000..86641ee60b7d --- /dev/null +++ b/docs/new-expensify/hubs/integrations/accounting-integrations.html @@ -0,0 +1,5 @@ +--- +layout: default +--- + +{% include section.html %} diff --git a/docs/new-expensify/hubs/integrations/index.html b/docs/new-expensify/hubs/integrations/index.html new file mode 100644 index 000000000000..d1f173534c8a --- /dev/null +++ b/docs/new-expensify/hubs/integrations/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Integrations +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/new-expensify/hubs/manage-employees-and-report-approvals/index.html b/docs/new-expensify/hubs/manage-employees-and-report-approvals/index.html new file mode 100644 index 000000000000..31e992f32d5d --- /dev/null +++ b/docs/new-expensify/hubs/manage-employees-and-report-approvals/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Manage Employees & Report Approvals +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/new-expensify/hubs/send-payments/index.html b/docs/new-expensify/hubs/send-payments/index.html new file mode 100644 index 000000000000..c8275af5c353 --- /dev/null +++ b/docs/new-expensify/hubs/send-payments/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Send Payments +--- + +{% include hub.html %} \ No newline at end of file diff --git a/docs/new-expensify/hubs/workspace-and-domain-settings/index.html b/docs/new-expensify/hubs/workspace-and-domain-settings/index.html new file mode 100644 index 000000000000..c4e5d06d6b8a --- /dev/null +++ b/docs/new-expensify/hubs/workspace-and-domain-settings/index.html @@ -0,0 +1,6 @@ +--- +layout: default +title: Workspace & Domain Settings +--- + +{% include hub.html %} \ No newline at end of file diff --git a/fastlane/Fastfile b/fastlane/Fastfile index ecec05f1cec1..c7d0f2f4f0f5 100644 --- a/fastlane/Fastfile +++ b/fastlane/Fastfile @@ -67,6 +67,8 @@ platform :android do desc "Build and upload app to Google Play" lane :beta do ENV["ENVFILE"]=".env.production" + # Google is very unreliable, so we retry a few times + ENV["SUPPLY_UPLOAD_MAX_RETRIES"]="5" gradle( project_dir: './android', @@ -86,6 +88,8 @@ platform :android do desc "Deploy app to Google Play production" lane :production do + # Google is very unreliable, so we retry a few times + ENV["SUPPLY_UPLOAD_MAX_RETRIES"]="5" google_play_track_version_codes( package_name: "com.expensify.chat", json_key: './android/app/android-fastlane-json-key.json', diff --git a/ios/NewExpensify/Info.plist b/ios/NewExpensify/Info.plist index 07e1cfae80ac..f41740a8bcb2 100644 --- a/ios/NewExpensify/Info.plist +++ b/ios/NewExpensify/Info.plist @@ -19,7 +19,7 @@ CFBundlePackageType APPL CFBundleShortVersionString - 1.3.71 + 1.3.74 CFBundleSignature ???? CFBundleURLTypes @@ -40,7 +40,7 @@ CFBundleVersion - 1.3.71.5 + 1.3.74.2 ITSAppUsesNonExemptEncryption LSApplicationQueriesSchemes diff --git a/ios/NewExpensifyTests/Info.plist b/ios/NewExpensifyTests/Info.plist index 49d12cf93594..95714ea2cc9f 100644 --- a/ios/NewExpensifyTests/Info.plist +++ b/ios/NewExpensifyTests/Info.plist @@ -15,10 +15,10 @@ CFBundlePackageType BNDL CFBundleShortVersionString - 1.3.71 + 1.3.74 CFBundleSignature ???? CFBundleVersion - 1.3.71.5 + 1.3.74.2 diff --git a/ios/Podfile.lock b/ios/Podfile.lock index aeb1887223cd..ba53d939e46c 100644 --- a/ios/Podfile.lock +++ b/ios/Podfile.lock @@ -31,14 +31,14 @@ PODS: - React-Core - CocoaAsyncSocket (7.6.5) - DoubleConversion (1.1.6) - - FBLazyVector (0.72.3) - - FBReactNativeSpec (0.72.3): + - FBLazyVector (0.72.4) + - FBReactNativeSpec (0.72.4): - RCT-Folly (= 2021.07.22.00) - - RCTRequired (= 0.72.3) - - RCTTypeSafety (= 0.72.3) - - React-Core (= 0.72.3) - - React-jsi (= 0.72.3) - - ReactCommon/turbomodule/core (= 0.72.3) + - RCTRequired (= 0.72.4) + - RCTTypeSafety (= 0.72.4) + - React-Core (= 0.72.4) + - React-jsi (= 0.72.4) + - ReactCommon/turbomodule/core (= 0.72.4) - Firebase/Analytics (8.8.0): - Firebase/Core - Firebase/Core (8.8.0): @@ -220,9 +220,9 @@ PODS: - AppAuth/Core (~> 1.6) - GTMSessionFetcher/Core (< 4.0, >= 1.5) - GTMSessionFetcher/Core (3.1.1) - - hermes-engine (0.72.3): - - hermes-engine/Pre-built (= 0.72.3) - - hermes-engine/Pre-built (0.72.3) + - hermes-engine (0.72.4): + - hermes-engine/Pre-built (= 0.72.4) + - hermes-engine/Pre-built (0.72.4) - libevent (2.1.12) - libwebp (1.2.4): - libwebp/demux (= 1.2.4) @@ -283,26 +283,26 @@ PODS: - fmt (~> 6.2.1) - glog - libevent - - RCTRequired (0.72.3) - - RCTTypeSafety (0.72.3): - - FBLazyVector (= 0.72.3) - - RCTRequired (= 0.72.3) - - React-Core (= 0.72.3) - - React (0.72.3): - - React-Core (= 0.72.3) - - React-Core/DevSupport (= 0.72.3) - - React-Core/RCTWebSocket (= 0.72.3) - - React-RCTActionSheet (= 0.72.3) - - React-RCTAnimation (= 0.72.3) - - React-RCTBlob (= 0.72.3) - - React-RCTImage (= 0.72.3) - - React-RCTLinking (= 0.72.3) - - React-RCTNetwork (= 0.72.3) - - React-RCTSettings (= 0.72.3) - - React-RCTText (= 0.72.3) - - React-RCTVibration (= 0.72.3) - - React-callinvoker (0.72.3) - - React-Codegen (0.72.3): + - RCTRequired (0.72.4) + - RCTTypeSafety (0.72.4): + - FBLazyVector (= 0.72.4) + - RCTRequired (= 0.72.4) + - React-Core (= 0.72.4) + - React (0.72.4): + - React-Core (= 0.72.4) + - React-Core/DevSupport (= 0.72.4) + - React-Core/RCTWebSocket (= 0.72.4) + - React-RCTActionSheet (= 0.72.4) + - React-RCTAnimation (= 0.72.4) + - React-RCTBlob (= 0.72.4) + - React-RCTImage (= 0.72.4) + - React-RCTLinking (= 0.72.4) + - React-RCTNetwork (= 0.72.4) + - React-RCTSettings (= 0.72.4) + - React-RCTText (= 0.72.4) + - React-RCTVibration (= 0.72.4) + - React-callinvoker (0.72.4) + - React-Codegen (0.72.4): - DoubleConversion - FBReactNativeSpec - glog @@ -317,11 +317,11 @@ PODS: - React-rncore - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core - - React-Core (0.72.3): + - React-Core (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) - - React-Core/Default (= 0.72.3) + - React-Core/Default (= 0.72.4) - React-cxxreact - React-hermes - React-jsi @@ -331,7 +331,7 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/CoreModulesHeaders (0.72.3): + - React-Core/CoreModulesHeaders (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) @@ -345,7 +345,7 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/Default (0.72.3): + - React-Core/Default (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) @@ -358,23 +358,23 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/DevSupport (0.72.3): + - React-Core/DevSupport (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) - - React-Core/Default (= 0.72.3) - - React-Core/RCTWebSocket (= 0.72.3) + - React-Core/Default (= 0.72.4) + - React-Core/RCTWebSocket (= 0.72.4) - React-cxxreact - React-hermes - React-jsi - React-jsiexecutor - - React-jsinspector (= 0.72.3) + - React-jsinspector (= 0.72.4) - React-perflogger - React-runtimeexecutor - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/RCTActionSheetHeaders (0.72.3): + - React-Core/RCTActionSheetHeaders (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) @@ -388,7 +388,7 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/RCTAnimationHeaders (0.72.3): + - React-Core/RCTAnimationHeaders (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) @@ -402,7 +402,7 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/RCTBlobHeaders (0.72.3): + - React-Core/RCTBlobHeaders (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) @@ -416,7 +416,7 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/RCTImageHeaders (0.72.3): + - React-Core/RCTImageHeaders (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) @@ -430,7 +430,7 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/RCTLinkingHeaders (0.72.3): + - React-Core/RCTLinkingHeaders (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) @@ -444,7 +444,7 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/RCTNetworkHeaders (0.72.3): + - React-Core/RCTNetworkHeaders (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) @@ -458,7 +458,7 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/RCTSettingsHeaders (0.72.3): + - React-Core/RCTSettingsHeaders (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) @@ -472,7 +472,7 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/RCTTextHeaders (0.72.3): + - React-Core/RCTTextHeaders (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) @@ -486,7 +486,7 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/RCTVibrationHeaders (0.72.3): + - React-Core/RCTVibrationHeaders (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) @@ -500,11 +500,11 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-Core/RCTWebSocket (0.72.3): + - React-Core/RCTWebSocket (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) - - React-Core/Default (= 0.72.3) + - React-Core/Default (= 0.72.4) - React-cxxreact - React-hermes - React-jsi @@ -514,57 +514,57 @@ PODS: - React-utils - SocketRocket (= 0.6.1) - Yoga - - React-CoreModules (0.72.3): + - React-CoreModules (0.72.4): - RCT-Folly (= 2021.07.22.00) - - RCTTypeSafety (= 0.72.3) - - React-Codegen (= 0.72.3) - - React-Core/CoreModulesHeaders (= 0.72.3) - - React-jsi (= 0.72.3) + - RCTTypeSafety (= 0.72.4) + - React-Codegen (= 0.72.4) + - React-Core/CoreModulesHeaders (= 0.72.4) + - React-jsi (= 0.72.4) - React-RCTBlob - - React-RCTImage (= 0.72.3) - - ReactCommon/turbomodule/core (= 0.72.3) + - React-RCTImage (= 0.72.4) + - ReactCommon/turbomodule/core (= 0.72.4) - SocketRocket (= 0.6.1) - - React-cxxreact (0.72.3): + - React-cxxreact (0.72.4): - boost (= 1.76.0) - DoubleConversion - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) - - React-callinvoker (= 0.72.3) - - React-debug (= 0.72.3) - - React-jsi (= 0.72.3) - - React-jsinspector (= 0.72.3) - - React-logger (= 0.72.3) - - React-perflogger (= 0.72.3) - - React-runtimeexecutor (= 0.72.3) - - React-debug (0.72.3) - - React-hermes (0.72.3): + - React-callinvoker (= 0.72.4) + - React-debug (= 0.72.4) + - React-jsi (= 0.72.4) + - React-jsinspector (= 0.72.4) + - React-logger (= 0.72.4) + - React-perflogger (= 0.72.4) + - React-runtimeexecutor (= 0.72.4) + - React-debug (0.72.4) + - React-hermes (0.72.4): - DoubleConversion - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) - RCT-Folly/Futures (= 2021.07.22.00) - - React-cxxreact (= 0.72.3) + - React-cxxreact (= 0.72.4) - React-jsi - - React-jsiexecutor (= 0.72.3) - - React-jsinspector (= 0.72.3) - - React-perflogger (= 0.72.3) - - React-jsi (0.72.3): + - React-jsiexecutor (= 0.72.4) + - React-jsinspector (= 0.72.4) + - React-perflogger (= 0.72.4) + - React-jsi (0.72.4): - boost (= 1.76.0) - DoubleConversion - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) - - React-jsiexecutor (0.72.3): + - React-jsiexecutor (0.72.4): - DoubleConversion - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) - - React-cxxreact (= 0.72.3) - - React-jsi (= 0.72.3) - - React-perflogger (= 0.72.3) - - React-jsinspector (0.72.3) - - React-logger (0.72.3): + - React-cxxreact (= 0.72.4) + - React-jsi (= 0.72.4) + - React-perflogger (= 0.72.4) + - React-jsinspector (0.72.4) + - React-logger (0.72.4): - glog - react-native-airship (15.2.6): - AirshipFrameworkProxy (= 2.0.8) @@ -593,7 +593,7 @@ PODS: - React-Core - react-native-pdf (6.7.1): - React-Core - - react-native-performance (4.0.0): + - react-native-performance (5.1.0): - React-Core - react-native-plaid-link-sdk (10.0.0): - Plaid (~> 4.1.0) @@ -614,7 +614,7 @@ PODS: - React-Core - react-native-webview (11.23.0): - React-Core - - React-NativeModulesApple (0.72.3): + - React-NativeModulesApple (0.72.4): - hermes-engine - React-callinvoker - React-Core @@ -623,17 +623,17 @@ PODS: - React-runtimeexecutor - ReactCommon/turbomodule/bridging - ReactCommon/turbomodule/core - - React-perflogger (0.72.3) - - React-RCTActionSheet (0.72.3): - - React-Core/RCTActionSheetHeaders (= 0.72.3) - - React-RCTAnimation (0.72.3): + - React-perflogger (0.72.4) + - React-RCTActionSheet (0.72.4): + - React-Core/RCTActionSheetHeaders (= 0.72.4) + - React-RCTAnimation (0.72.4): - RCT-Folly (= 2021.07.22.00) - - RCTTypeSafety (= 0.72.3) - - React-Codegen (= 0.72.3) - - React-Core/RCTAnimationHeaders (= 0.72.3) - - React-jsi (= 0.72.3) - - ReactCommon/turbomodule/core (= 0.72.3) - - React-RCTAppDelegate (0.72.3): + - RCTTypeSafety (= 0.72.4) + - React-Codegen (= 0.72.4) + - React-Core/RCTAnimationHeaders (= 0.72.4) + - React-jsi (= 0.72.4) + - ReactCommon/turbomodule/core (= 0.72.4) + - React-RCTAppDelegate (0.72.4): - RCT-Folly - RCTRequired - RCTTypeSafety @@ -645,54 +645,54 @@ PODS: - React-RCTNetwork - React-runtimescheduler - ReactCommon/turbomodule/core - - React-RCTBlob (0.72.3): + - React-RCTBlob (0.72.4): - hermes-engine - RCT-Folly (= 2021.07.22.00) - - React-Codegen (= 0.72.3) - - React-Core/RCTBlobHeaders (= 0.72.3) - - React-Core/RCTWebSocket (= 0.72.3) - - React-jsi (= 0.72.3) - - React-RCTNetwork (= 0.72.3) - - ReactCommon/turbomodule/core (= 0.72.3) - - React-RCTImage (0.72.3): + - React-Codegen (= 0.72.4) + - React-Core/RCTBlobHeaders (= 0.72.4) + - React-Core/RCTWebSocket (= 0.72.4) + - React-jsi (= 0.72.4) + - React-RCTNetwork (= 0.72.4) + - ReactCommon/turbomodule/core (= 0.72.4) + - React-RCTImage (0.72.4): - RCT-Folly (= 2021.07.22.00) - - RCTTypeSafety (= 0.72.3) - - React-Codegen (= 0.72.3) - - React-Core/RCTImageHeaders (= 0.72.3) - - React-jsi (= 0.72.3) - - React-RCTNetwork (= 0.72.3) - - ReactCommon/turbomodule/core (= 0.72.3) - - React-RCTLinking (0.72.3): - - React-Codegen (= 0.72.3) - - React-Core/RCTLinkingHeaders (= 0.72.3) - - React-jsi (= 0.72.3) - - ReactCommon/turbomodule/core (= 0.72.3) - - React-RCTNetwork (0.72.3): + - RCTTypeSafety (= 0.72.4) + - React-Codegen (= 0.72.4) + - React-Core/RCTImageHeaders (= 0.72.4) + - React-jsi (= 0.72.4) + - React-RCTNetwork (= 0.72.4) + - ReactCommon/turbomodule/core (= 0.72.4) + - React-RCTLinking (0.72.4): + - React-Codegen (= 0.72.4) + - React-Core/RCTLinkingHeaders (= 0.72.4) + - React-jsi (= 0.72.4) + - ReactCommon/turbomodule/core (= 0.72.4) + - React-RCTNetwork (0.72.4): - RCT-Folly (= 2021.07.22.00) - - RCTTypeSafety (= 0.72.3) - - React-Codegen (= 0.72.3) - - React-Core/RCTNetworkHeaders (= 0.72.3) - - React-jsi (= 0.72.3) - - ReactCommon/turbomodule/core (= 0.72.3) - - React-RCTSettings (0.72.3): + - RCTTypeSafety (= 0.72.4) + - React-Codegen (= 0.72.4) + - React-Core/RCTNetworkHeaders (= 0.72.4) + - React-jsi (= 0.72.4) + - ReactCommon/turbomodule/core (= 0.72.4) + - React-RCTSettings (0.72.4): - RCT-Folly (= 2021.07.22.00) - - RCTTypeSafety (= 0.72.3) - - React-Codegen (= 0.72.3) - - React-Core/RCTSettingsHeaders (= 0.72.3) - - React-jsi (= 0.72.3) - - ReactCommon/turbomodule/core (= 0.72.3) - - React-RCTText (0.72.3): - - React-Core/RCTTextHeaders (= 0.72.3) - - React-RCTVibration (0.72.3): + - RCTTypeSafety (= 0.72.4) + - React-Codegen (= 0.72.4) + - React-Core/RCTSettingsHeaders (= 0.72.4) + - React-jsi (= 0.72.4) + - ReactCommon/turbomodule/core (= 0.72.4) + - React-RCTText (0.72.4): + - React-Core/RCTTextHeaders (= 0.72.4) + - React-RCTVibration (0.72.4): - RCT-Folly (= 2021.07.22.00) - - React-Codegen (= 0.72.3) - - React-Core/RCTVibrationHeaders (= 0.72.3) - - React-jsi (= 0.72.3) - - ReactCommon/turbomodule/core (= 0.72.3) - - React-rncore (0.72.3) - - React-runtimeexecutor (0.72.3): - - React-jsi (= 0.72.3) - - React-runtimescheduler (0.72.3): + - React-Codegen (= 0.72.4) + - React-Core/RCTVibrationHeaders (= 0.72.4) + - React-jsi (= 0.72.4) + - ReactCommon/turbomodule/core (= 0.72.4) + - React-rncore (0.72.4) + - React-runtimeexecutor (0.72.4): + - React-jsi (= 0.72.4) + - React-runtimescheduler (0.72.4): - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) @@ -700,30 +700,30 @@ PODS: - React-debug - React-jsi - React-runtimeexecutor - - React-utils (0.72.3): + - React-utils (0.72.4): - glog - RCT-Folly (= 2021.07.22.00) - React-debug - - ReactCommon/turbomodule/bridging (0.72.3): + - ReactCommon/turbomodule/bridging (0.72.4): - DoubleConversion - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) - - React-callinvoker (= 0.72.3) - - React-cxxreact (= 0.72.3) - - React-jsi (= 0.72.3) - - React-logger (= 0.72.3) - - React-perflogger (= 0.72.3) - - ReactCommon/turbomodule/core (0.72.3): + - React-callinvoker (= 0.72.4) + - React-cxxreact (= 0.72.4) + - React-jsi (= 0.72.4) + - React-logger (= 0.72.4) + - React-perflogger (= 0.72.4) + - ReactCommon/turbomodule/core (0.72.4): - DoubleConversion - glog - hermes-engine - RCT-Folly (= 2021.07.22.00) - - React-callinvoker (= 0.72.3) - - React-cxxreact (= 0.72.3) - - React-jsi (= 0.72.3) - - React-logger (= 0.72.3) - - React-perflogger (= 0.72.3) + - React-callinvoker (= 0.72.4) + - React-cxxreact (= 0.72.4) + - React-jsi (= 0.72.4) + - React-logger (= 0.72.4) + - React-perflogger (= 0.72.4) - RNAppleAuthentication (2.2.2): - React-Core - RNCAsyncStorage (1.17.11): @@ -783,7 +783,7 @@ PODS: - React-Core - RNReactNativeHapticFeedback (1.14.0): - React-Core - - RNReanimated (3.4.0): + - RNReanimated (3.5.4): - DoubleConversion - FBLazyVector - glog @@ -815,7 +815,7 @@ PODS: - RNScreens (3.21.0): - React-Core - React-RCTImage - - RNSVG (13.9.0): + - RNSVG (13.13.0): - React-Core - SDWebImage (5.11.1): - SDWebImage/Core (= 5.11.1) @@ -1010,7 +1010,7 @@ EXTERNAL SOURCES: :podspec: "../node_modules/react-native/third-party-podspecs/glog.podspec" hermes-engine: :podspec: "../node_modules/react-native/sdks/hermes-engine/hermes-engine.podspec" - :tag: hermes-2023-03-20-RNv0.72.0-49794cfc7c81fb8f69fd60c3bbf85a7480cc5a77 + :tag: hermes-2023-08-07-RNv0.72.4-813b2def12bc9df02654b3e3653ae4a68d0572e0 lottie-react-native: :path: "../node_modules/lottie-react-native" onfido-react-native-sdk: @@ -1182,8 +1182,8 @@ SPEC CHECKSUMS: BVLinearGradient: 421743791a59d259aec53f4c58793aad031da2ca CocoaAsyncSocket: 065fd1e645c7abab64f7a6a2007a48038fdc6a99 DoubleConversion: 5189b271737e1565bdce30deb4a08d647e3f5f54 - FBLazyVector: 4cce221dd782d3ff7c4172167bba09d58af67ccb - FBReactNativeSpec: c6bd9e179757b3c0ecf815864fae8032377903ef + FBLazyVector: 5d4a3b7f411219a45a6d952f77d2c0a6c9989da5 + FBReactNativeSpec: 3fc2d478e1c4b08276f9dd9128f80ec6d5d85c1f Firebase: 629510f1a9ddb235f3a7c5c8ceb23ba887f0f814 FirebaseABTesting: 10cbce8db9985ae2e3847ea44e9947dd18f94e10 FirebaseAnalytics: 5506ea8b867d8423485a84b4cd612d279f7b0b8a @@ -1209,7 +1209,7 @@ SPEC CHECKSUMS: GoogleUtilities: 9aa0ad5a7bc171f8bae016300bfcfa3fb8425749 GTMAppAuth: 99fb010047ba3973b7026e45393f51f27ab965ae GTMSessionFetcher: e8647203b65cee28c5f73d0f473d096653945e72 - hermes-engine: 10fbd3f62405c41ea07e71973ea61e1878d07322 + hermes-engine: 81191603c4eaa01f5e4ae5737a9efcf64756c7b2 libevent: 4049cae6c81cdb3654a443be001fb9bdceff7913 libwebp: f62cb61d0a484ba548448a4bd52aabf150ff6eef lottie-ios: 8f97d3271e155c2d688875c29cd3c74908aef5f8 @@ -1229,20 +1229,20 @@ SPEC CHECKSUMS: Plaid: 7d340abeadb46c7aa1a91f896c5b22395a31fcf2 PromisesObjC: 09985d6d70fbe7878040aa746d78236e6946d2ef RCT-Folly: 424b8c9a7a0b9ab2886ffe9c3b041ef628fd4fb1 - RCTRequired: a2faf4bad4e438ca37b2040cb8f7799baa065c18 - RCTTypeSafety: cb09f3e4747b6d18331a15eb05271de7441ca0b3 - React: 13109005b5353095c052f26af37413340ccf7a5d - React-callinvoker: c8c87bce983aa499c13cb06d4447c025a35274d6 - React-Codegen: 712d523524d89d71f1cf7cc624854941be983c4d - React-Core: 688f88b7f3a3d30b4848036223f8b07102c687e5 - React-CoreModules: 63c063a3ade8fb3b1bec5fd9a50f17b0421558c6 - React-cxxreact: 37765b4975541105b2a3322a4b473417c158c869 - React-debug: 51f11ef8db14b47f24e71c42a4916d4192972156 - React-hermes: 935ae71fb3d7654e947beba8498835cd5e479707 - React-jsi: ec628dc7a15ffea969f237b0ea6d2fde212b19dd - React-jsiexecutor: 59d1eb03af7d30b7d66589c410f13151271e8006 - React-jsinspector: b511447170f561157547bc0bef3f169663860be7 - React-logger: c5b527272d5f22eaa09bb3c3a690fee8f237ae95 + RCTRequired: c0569ecc035894e4a68baecb30fe6a7ea6e399f9 + RCTTypeSafety: e90354072c21236e0bcf1699011e39acd25fea2f + React: a1be3c6dc0a6e949ccd3e659781aa47bbae1868f + React-callinvoker: 1020b33f6cb1a1824f9ca2a86609fbce2a73c6ed + React-Codegen: a0a26badf098d4a779acda922caf74f6ecabed28 + React-Core: 52075b80f10c26f62219d7b5d13d7d8089f027b3 + React-CoreModules: 21abab85d7ad9038ce2b1c33d39e3baaf7dc9244 + React-cxxreact: 4ad1cc861e32fb533dad6ff7a4ea25680fa1c994 + React-debug: 17366a3d5c5d2f5fc04f09101a4af38cb42b54ae + React-hermes: 37377d0a56aa0cf55c65248271866ce3268cde3f + React-jsi: 6de8b0ccc6b765b58e4eee9ee38049dbeaf5c221 + React-jsiexecutor: c7f826e40fa9cab5d37cab6130b1af237332b594 + React-jsinspector: aaed4cf551c4a1c98092436518c2d267b13a673f + React-logger: da1ebe05ae06eb6db4b162202faeafac4b435e77 react-native-airship: 5d19f4ba303481cf4101ff9dee9249ef6a8a6b64 react-native-blob-util: 99f4d79189252f597fe0d810c57a3733b1b1dea6 react-native-cameraroll: 8ffb0af7a5e5de225fd667610e2979fc1f0c2151 @@ -1255,30 +1255,30 @@ SPEC CHECKSUMS: react-native-netinfo: ccbe1085dffd16592791d550189772e13bf479e2 react-native-pager-view: 0ccb8bf60e2ebd38b1f3669fa3650ecce81db2df react-native-pdf: 7c0e91ada997bac8bac3bb5bea5b6b81f5a3caae - react-native-performance: 224bd53e6a835fda4353302cf891d088a0af7406 + react-native-performance: cef2b618d47b277fb5c3280b81a3aad1e72f2886 react-native-plaid-link-sdk: 9eb0f71dad94b3bdde649c7a384cba93024af46c react-native-quick-sqlite: bcc7a7a250a40222f18913a97cd356bf82d0a6c4 react-native-render-html: 96c979fe7452a0a41559685d2f83b12b93edac8c react-native-safe-area-context: 99b24a0c5acd0d5dcac2b1a7f18c49ea317be99a react-native-view-shot: 705f999ac2a24e4e6c909c0ca65c732ed33ca2ff react-native-webview: e771bc375f789ebfa02a26939a57dbc6fa897336 - React-NativeModulesApple: c57f3efe0df288a6532b726ad2d0322a9bf38472 - React-perflogger: 6bd153e776e6beed54c56b0847e1220a3ff92ba5 - React-RCTActionSheet: c0b62af44e610e69d9a2049a682f5dba4e9dff17 - React-RCTAnimation: f9bf9719258926aea9ecb8a2aa2595d3ff9a6022 - React-RCTAppDelegate: e5ac35d4dbd1fae7df3a62b47db04b6a8d151592 - React-RCTBlob: c4f1e69a6ef739aa42586b876d637dab4e3b5bed - React-RCTImage: e5798f01aba248416c02a506cf5e6dfcba827638 - React-RCTLinking: f5b6227c879e33206f34e68924c458f57bbb96d9 - React-RCTNetwork: d5554fbfac1c618da3c8fa29933108ea22837788 - React-RCTSettings: 189c71e3e6146ba59f4f7e2cbeb494cf2ad42afa - React-RCTText: 19425aea9d8b6ccae55a27916355b17ab577e56e - React-RCTVibration: 388ac0e1455420895d1ca2548401eed964b038a6 - React-rncore: 755a331dd67b74662108f2d66a384454bf8dc1a1 - React-runtimeexecutor: 369ae9bb3f83b65201c0c8f7d50b72280b5a1dbc - React-runtimescheduler: 837c1bebd2f84572db17698cd702ceaf585b0d9a - React-utils: bcb57da67eec2711f8b353f6e3d33bd8e4b2efa3 - ReactCommon: 3ccb8fb14e6b3277e38c73b0ff5e4a1b8db017a9 + React-NativeModulesApple: edb5ace14f73f4969df6e7b1f3e41bef0012740f + React-perflogger: 496a1a3dc6737f964107cb3ddae7f9e265ddda58 + React-RCTActionSheet: 02904b932b50e680f4e26e7a686b33ebf7ef3c00 + React-RCTAnimation: 88feaf0a85648fb8fd497ce749829774910276d6 + React-RCTAppDelegate: 5792ac0f0feccb584765fdd7aa81ea320c4d9b0b + React-RCTBlob: 0dbc9e2a13d241b37d46b53e54630cbad1f0e141 + React-RCTImage: b111645ab901f8e59fc68fbe31f5731bdbeef087 + React-RCTLinking: 3d719727b4c098aad3588aa3559361ee0579f5de + React-RCTNetwork: b44d3580be05d74556ba4efbf53570f17e38f734 + React-RCTSettings: c0c54b330442c29874cd4dae6e94190dc11a6f6f + React-RCTText: 9b9f5589d9b649d7246c3f336e116496df28cfe6 + React-RCTVibration: 691c67f3beaf1d084ceed5eb5c1dddd9afa8591e + React-rncore: 142268f6c92e296dc079aadda3fade778562f9e4 + React-runtimeexecutor: d465ba0c47ef3ed8281143f59605cacc2244d5c7 + React-runtimescheduler: 4941cc1b3cf08b792fbf666342c9fc95f1969035 + React-utils: b79f2411931f9d3ea5781404dcbb2fa8a837e13a + ReactCommon: 4b2bdcb50a3543e1c2b2849ad44533686610826d RNAppleAuthentication: 0571c08da8c327ae2afc0261b48b4a515b0286a6 RNCAsyncStorage: 8616bd5a58af409453ea4e1b246521bb76578d60 RNCClipboard: 41d8d918092ae8e676f18adada19104fa3e68495 @@ -1298,15 +1298,15 @@ SPEC CHECKSUMS: rnmapbox-maps: 6f638ec002aa6e906a6f766d69cd45f968d98e64 RNPermissions: dcdb7b99796bbeda6975a6e79ad519c41b251b1c RNReactNativeHapticFeedback: 1e3efeca9628ff9876ee7cdd9edec1b336913f8c - RNReanimated: 020859659f64be2d30849a1fe88c821a7c3e0cbf + RNReanimated: ab2e96c6d5591c3dfbb38a464f54c8d17fb34a87 RNScreens: d037903436160a4b039d32606668350d2a808806 - RNSVG: 53c661b76829783cdaf9b7a57258f3d3b4c28315 + RNSVG: ed492aaf3af9ca01bc945f7a149d76d62e73ec82 SDWebImage: a7f831e1a65eb5e285e3fb046a23fcfbf08e696d SDWebImageWebPCoder: 908b83b6adda48effe7667cd2b7f78c897e5111d SocketRocket: f32cd54efbe0f095c4d7594881e52619cfe80b17 Turf: 469ce2c3d22e5e8e4818d5a3b254699a5c89efa4 VisionCamera: d3ec8883417a6a4a0e3a6ba37d81d22db7611601 - Yoga: 8796b55dba14d7004f980b54bcc9833ee45b28ce + Yoga: 3efc43e0d48686ce2e8c60f99d4e6bd349aff981 YogaKit: f782866e155069a2cca2517aafea43200b01fd5a PODFILE CHECKSUM: 2daf34c870819a933f3fefe426801d54b2ff2a14 diff --git a/jest.config.js b/jest.config.js index 1f540a679b9a..6cf44b6b3695 100644 --- a/jest.config.js +++ b/jest.config.js @@ -23,6 +23,6 @@ module.exports = { }, testEnvironment: 'jsdom', setupFiles: ['/jest/setup.js', './node_modules/@react-native-google-signin/google-signin/jest/build/setup.js'], - setupFilesAfterEnv: ['@testing-library/jest-native/extend-expect'], + setupFilesAfterEnv: ['@testing-library/jest-native/extend-expect', '/jest/setupAfterEnv.js'], cacheDirectory: '/.jest-cache', }; diff --git a/jest/setupAfterEnv.js b/jest/setupAfterEnv.js new file mode 100644 index 000000000000..6f7836b64dbb --- /dev/null +++ b/jest/setupAfterEnv.js @@ -0,0 +1 @@ +jest.useRealTimers(); diff --git a/package-lock.json b/package-lock.json index 68ea17fc20b8..64ee3cf6308f 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "new.expensify", - "version": "1.3.71-5", + "version": "1.3.74-2", "lockfileVersion": 2, "requires": true, "packages": { "": { "name": "new.expensify", - "version": "1.3.71-5", + "version": "1.3.74-2", "hasInstallScript": true, "license": "MIT", "dependencies": { @@ -50,7 +50,7 @@ "date-fns-tz": "^2.0.0", "dom-serializer": "^0.2.2", "domhandler": "^4.3.0", - "expensify-common": "git+ssh://git@github.com/Expensify/expensify-common.git#35bff866a8d345b460ea6256f0a0f0a8a7f81086", + "expensify-common": "git+ssh://git@github.com/Expensify/expensify-common.git#1609f1848cc0c2528064519c3ea48b4953a708ee", "fbjs": "^3.0.2", "htmlparser2": "^7.2.0", "idb-keyval": "^6.2.1", @@ -71,7 +71,7 @@ "react-dom": "18.1.0", "react-error-boundary": "^4.0.11", "react-map-gl": "^7.1.3", - "react-native": "0.72.3", + "react-native": "0.72.4", "react-native-blob-util": "^0.17.3", "react-native-collapsible": "^1.6.0", "react-native-config": "^1.4.5", @@ -81,7 +81,7 @@ "react-native-fast-image": "^8.6.3", "react-native-fs": "^2.20.0", "react-native-gesture-handler": "2.12.0", - "react-native-google-places-autocomplete": "git+https://github.com/Expensify/react-native-google-places-autocomplete.git#ee87343c3e827ff7818abc71b6bb04fcc1f120e0", + "react-native-google-places-autocomplete": "git+https://github.com/Expensify/react-native-google-places-autocomplete.git#cef3ac29d9501091453136e1219e24c4ec9f9d76", "react-native-haptic-feedback": "^1.13.0", "react-native-image-pan-zoom": "^2.1.12", "react-native-image-picker": "^5.1.0", @@ -90,7 +90,7 @@ "react-native-linear-gradient": "^2.8.1", "react-native-localize": "^2.2.6", "react-native-modal": "^13.0.0", - "react-native-onyx": "1.0.77", + "react-native-onyx": "1.0.87", "react-native-pager-view": "^6.2.0", "react-native-pdf": "^6.7.1", "react-native-performance": "^5.1.0", @@ -99,7 +99,7 @@ "react-native-plaid-link-sdk": "^10.0.0", "react-native-qrcode-svg": "^6.2.0", "react-native-quick-sqlite": "^8.0.0-beta.2", - "react-native-reanimated": "3.4.0", + "react-native-reanimated": "3.5.4", "react-native-render-html": "6.3.1", "react-native-safe-area-context": "4.4.1", "react-native-screens": "3.21.0", @@ -139,7 +139,7 @@ "@octokit/plugin-paginate-rest": "3.1.0", "@octokit/plugin-throttling": "4.1.0", "@react-native-community/eslint-config": "3.0.0", - "@react-native/metro-config": "^0.72.9", + "@react-native/metro-config": "^0.72.11", "@react-navigation/devtools": "^6.0.10", "@storybook/addon-a11y": "^6.5.9", "@storybook/addon-essentials": "^7.0.0", @@ -190,7 +190,7 @@ "electron-builder": "24.6.4", "eslint": "^7.6.0", "eslint-config-airbnb-typescript": "^17.1.0", - "eslint-config-expensify": "^2.0.38", + "eslint-config-expensify": "^2.0.39", "eslint-config-prettier": "^8.8.0", "eslint-plugin-jest": "^24.1.0", "eslint-plugin-jsdoc": "^46.2.6", @@ -204,7 +204,7 @@ "jest-circus": "29.4.1", "jest-cli": "29.4.1", "jest-environment-jsdom": "^29.4.1", - "metro-react-native-babel-preset": "0.76.7", + "metro-react-native-babel-preset": "0.76.8", "mock-fs": "^4.13.0", "onchange": "^7.1.0", "portfinder": "^1.0.28", @@ -1777,10 +1777,11 @@ } }, "node_modules/@babel/plugin-transform-object-assign": { - "version": "7.18.6", - "license": "MIT", + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-object-assign/-/plugin-transform-object-assign-7.22.5.tgz", + "integrity": "sha512-iDhx9ARkXq4vhZ2CYOSnQXkmxkDgosLi3J8Z17mKz7LyzthtkdVchLD7WZ3aXeCuvJDOW3+1I5TpJmwIbF9MKQ==", "dependencies": { - "@babel/helper-plugin-utils": "^7.18.6" + "@babel/helper-plugin-utils": "^7.22.5" }, "engines": { "node": ">=6.9.0" @@ -6726,19 +6727,19 @@ } }, "node_modules/@react-native-community/cli": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli/-/cli-11.3.5.tgz", - "integrity": "sha512-wMXgKEWe6uesw7vyXKKjx5EDRog0QdXHxdgRguG14AjQRao1+4gXEWq2yyExOTi/GDY6dfJBUGTCwGQxhnk/Lg==", - "dependencies": { - "@react-native-community/cli-clean": "11.3.5", - "@react-native-community/cli-config": "11.3.5", - "@react-native-community/cli-debugger-ui": "11.3.5", - "@react-native-community/cli-doctor": "11.3.5", - "@react-native-community/cli-hermes": "11.3.5", - "@react-native-community/cli-plugin-metro": "11.3.5", - "@react-native-community/cli-server-api": "11.3.5", - "@react-native-community/cli-tools": "11.3.5", - "@react-native-community/cli-types": "11.3.5", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli/-/cli-11.3.6.tgz", + "integrity": "sha512-bdwOIYTBVQ9VK34dsf6t3u6vOUU5lfdhKaAxiAVArjsr7Je88Bgs4sAbsOYsNK3tkE8G77U6wLpekknXcanlww==", + "dependencies": { + "@react-native-community/cli-clean": "11.3.6", + "@react-native-community/cli-config": "11.3.6", + "@react-native-community/cli-debugger-ui": "11.3.6", + "@react-native-community/cli-doctor": "11.3.6", + "@react-native-community/cli-hermes": "11.3.6", + "@react-native-community/cli-plugin-metro": "11.3.6", + "@react-native-community/cli-server-api": "11.3.6", + "@react-native-community/cli-tools": "11.3.6", + "@react-native-community/cli-types": "11.3.6", "chalk": "^4.1.2", "commander": "^9.4.1", "execa": "^5.0.0", @@ -6746,7 +6747,7 @@ "fs-extra": "^8.1.0", "graceful-fs": "^4.1.3", "prompts": "^2.4.0", - "semver": "^6.3.0" + "semver": "^7.5.2" }, "bin": { "react-native": "build/bin.js" @@ -6756,11 +6757,11 @@ } }, "node_modules/@react-native-community/cli-clean": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-clean/-/cli-clean-11.3.5.tgz", - "integrity": "sha512-1+7BU962wKkIkHRp/uW3jYbQKKGtU7L+R3g59D8K6uLccuxJYUBJv18753ojMa6SD3SAq5Xh31bAre+YwVcOTA==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-clean/-/cli-clean-11.3.6.tgz", + "integrity": "sha512-jOOaeG5ebSXTHweq1NznVJVAFKtTFWL4lWgUXl845bCGX7t1lL8xQNWHKwT8Oh1pGR2CI3cKmRjY4hBg+pEI9g==", "dependencies": { - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "execa": "^5.0.0", "prompts": "^2.4.0" @@ -6831,11 +6832,11 @@ } }, "node_modules/@react-native-community/cli-config": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-config/-/cli-config-11.3.5.tgz", - "integrity": "sha512-fMblIsHlUleKfGsgWyjFJYfx1SqrsnhS/QXfA8w7iT6GrNOOjBp5UWx8+xlMDFcmOb9e42g1ExFDKl3n8FWkxQ==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-config/-/cli-config-11.3.6.tgz", + "integrity": "sha512-edy7fwllSFLan/6BG6/rznOBCLPrjmJAE10FzkEqNLHowi0bckiAPg1+1jlgQ2qqAxV5kuk+c9eajVfQvPLYDA==", "dependencies": { - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "cosmiconfig": "^5.1.0", "deepmerge": "^4.3.0", @@ -6954,22 +6955,22 @@ } }, "node_modules/@react-native-community/cli-debugger-ui": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-debugger-ui/-/cli-debugger-ui-11.3.5.tgz", - "integrity": "sha512-o5JVCKEpPUXMX4r3p1cYjiy3FgdOEkezZcQ6owWEae2dYvV19lLYyJwnocm9Y7aG9PvpgI3PIMVh3KZbhS21eA==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-debugger-ui/-/cli-debugger-ui-11.3.6.tgz", + "integrity": "sha512-jhMOSN/iOlid9jn/A2/uf7HbC3u7+lGktpeGSLnHNw21iahFBzcpuO71ekEdlmTZ4zC/WyxBXw9j2ka33T358w==", "dependencies": { "serve-static": "^1.13.1" } }, "node_modules/@react-native-community/cli-doctor": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-doctor/-/cli-doctor-11.3.5.tgz", - "integrity": "sha512-+4BuFHjoV4FFjX5y60l0s6nS0agidb1izTVwsFixeFKW73LUkOLu+Ae5HI94RAFEPE4ePEVNgYX3FynIau6K0g==", - "dependencies": { - "@react-native-community/cli-config": "11.3.5", - "@react-native-community/cli-platform-android": "11.3.5", - "@react-native-community/cli-platform-ios": "11.3.5", - "@react-native-community/cli-tools": "11.3.5", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-doctor/-/cli-doctor-11.3.6.tgz", + "integrity": "sha512-UT/Tt6omVPi1j6JEX+CObc85eVFghSZwy4GR9JFMsO7gNg2Tvcu1RGWlUkrbmWMAMHw127LUu6TGK66Ugu1NLA==", + "dependencies": { + "@react-native-community/cli-config": "11.3.6", + "@react-native-community/cli-platform-android": "11.3.6", + "@react-native-community/cli-platform-ios": "11.3.6", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "command-exists": "^1.2.8", "envinfo": "^7.7.2", @@ -6979,7 +6980,7 @@ "node-stream-zip": "^1.9.1", "ora": "^5.4.1", "prompts": "^2.4.0", - "semver": "^6.3.0", + "semver": "^7.5.2", "strip-ansi": "^5.2.0", "sudo-prompt": "^9.0.0", "wcwidth": "^1.0.1", @@ -7044,14 +7045,6 @@ "resolved": "https://registry.npmjs.org/ip/-/ip-1.1.8.tgz", "integrity": "sha512-PuExPYUiu6qMBQb4l06ecm6T6ujzhmh+MeJcW9wa89PoAz5pvd4zPgN5WJV104mb6S2T1AwNIAaB70JNrLQWhg==" }, - "node_modules/@react-native-community/cli-doctor/node_modules/semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", - "bin": { - "semver": "bin/semver.js" - } - }, "node_modules/@react-native-community/cli-doctor/node_modules/strip-ansi": { "version": "5.2.0", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-5.2.0.tgz", @@ -7075,12 +7068,12 @@ } }, "node_modules/@react-native-community/cli-hermes": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-hermes/-/cli-hermes-11.3.5.tgz", - "integrity": "sha512-+3m34hiaJpFel8BlJE7kJOaPzWR/8U8APZG2LXojbAdBAg99EGmQcwXIgsSVJFvH8h/nezf4DHbsPKigIe33zA==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-hermes/-/cli-hermes-11.3.6.tgz", + "integrity": "sha512-O55YAYGZ3XynpUdePPVvNuUPGPY0IJdctLAOHme73OvS80gNwfntHDXfmY70TGHWIfkK2zBhA0B+2v8s5aTyTA==", "dependencies": { - "@react-native-community/cli-platform-android": "11.3.5", - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-platform-android": "11.3.6", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "hermes-profile-transformer": "^0.0.6", "ip": "^1.1.5" @@ -7156,11 +7149,11 @@ } }, "node_modules/@react-native-community/cli-platform-android": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-platform-android/-/cli-platform-android-11.3.5.tgz", - "integrity": "sha512-s4Lj7FKxJ/BofGi/ifjPfrA9MjFwIgYpHnHBSlqtbsvPoSYzmVCU2qlWM8fb3AmkXIwyYt4A6MEr3MmNT2UoBg==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-platform-android/-/cli-platform-android-11.3.6.tgz", + "integrity": "sha512-ZARrpLv5tn3rmhZc//IuDM1LSAdYnjUmjrp58RynlvjLDI4ZEjBAGCQmgysRgXAsK7ekMrfkZgemUczfn9td2A==", "dependencies": { - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "execa": "^5.0.0", "glob": "^7.1.3", @@ -7232,11 +7225,11 @@ } }, "node_modules/@react-native-community/cli-platform-ios": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-platform-ios/-/cli-platform-ios-11.3.5.tgz", - "integrity": "sha512-ytJC/YCFD7P+KuQHOT5Jzh1ho2XbJEjq71yHa1gJP2PG/Q/uB4h1x2XpxDqv5iXU6E250yjvKMmkReKTW4CTig==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-platform-ios/-/cli-platform-ios-11.3.6.tgz", + "integrity": "sha512-tZ9VbXWiRW+F+fbZzpLMZlj93g3Q96HpuMsS6DRhrTiG+vMQ3o6oPWSEEmMGOvJSYU7+y68Dc9ms2liC7VD6cw==", "dependencies": { - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "execa": "^5.0.0", "fast-xml-parser": "^4.0.12", @@ -7309,12 +7302,12 @@ } }, "node_modules/@react-native-community/cli-plugin-metro": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-plugin-metro/-/cli-plugin-metro-11.3.5.tgz", - "integrity": "sha512-r9AekfeLKdblB7LfWB71IrNy1XM03WrByQlUQajUOZAP2NmUUBLl9pMZscPjJeOSgLpHB9ixEFTIOhTabri/qg==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-plugin-metro/-/cli-plugin-metro-11.3.6.tgz", + "integrity": "sha512-D97racrPX3069ibyabJNKw9aJpVcaZrkYiEzsEnx50uauQtPDoQ1ELb/5c6CtMhAEGKoZ0B5MS23BbsSZcLs2g==", "dependencies": { - "@react-native-community/cli-server-api": "11.3.5", - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-server-api": "11.3.6", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "execa": "^5.0.0", "metro": "0.76.7", @@ -7326,6 +7319,29 @@ "readline": "^1.3.0" } }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dependencies": { + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/@types/yargs": { + "version": "16.0.5", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.5.tgz", + "integrity": "sha512-AxO/ADJOBFJScHbWhq2xAhlWP24rY4aCEG/NFaMvbT3X2MgRsLjhjQwsn0Zi5zn0LG9jUhCCZMeX9Dkuw6k+vQ==", + "dependencies": { + "@types/yargs-parser": "*" + } + }, "node_modules/@react-native-community/cli-plugin-metro/node_modules/ansi-styles": { "version": "4.3.0", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", @@ -7355,6 +7371,24 @@ "url": "https://github.com/chalk/chalk?sponsor=1" } }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/ci-info": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-2.0.0.tgz", + "integrity": "sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==" + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/cliui": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", + "integrity": "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==", + "dependencies": { + "string-width": "^4.2.0", + "strip-ansi": "^6.0.1", + "wrap-ansi": "^7.0.0" + }, + "engines": { + "node": ">=12" + } + }, "node_modules/@react-native-community/cli-plugin-metro/node_modules/color-convert": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", @@ -7371,6 +7405,28 @@ "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/cosmiconfig": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-5.2.1.tgz", + "integrity": "sha512-H65gsXo1SKjf8zmrJ67eJk8aIRKV5ff2D4uKZIBZShbhGSpEmsQOPW/SKMKYhSTrqR7ufy6RP69rPogdaPh/kA==", + "dependencies": { + "import-fresh": "^2.0.0", + "is-directory": "^0.3.1", + "js-yaml": "^3.13.1", + "parse-json": "^4.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dependencies": { + "ms": "2.0.0" + } + }, "node_modules/@react-native-community/cli-plugin-metro/node_modules/has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", @@ -7379,6 +7435,492 @@ "node": ">=8" } }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/import-fresh": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-2.0.0.tgz", + "integrity": "sha512-eZ5H8rcgYazHbKC3PG4ClHNykCSxtAhxSSEM+2mb+7evD2CKF5V7c0dNum7AdpDh0ZdICwZY9sRSn8f+KH96sg==", + "dependencies": { + "caller-path": "^2.0.0", + "resolve-from": "^3.0.0" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/jest-regex-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-regex-util/-/jest-regex-util-27.5.1.tgz", + "integrity": "sha512-4bfKq2zie+x16okqDXjXn9ql2B0dScQu+vcwe4TvFVhkVyuWLqpZrZtXxLLWoXYgn0E87I6r6GRYHF7wFZBUvg==", + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", + "dependencies": { + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" + }, + "engines": { + "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/jest-util/node_modules/ci-info": { + "version": "3.8.0", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-3.8.0.tgz", + "integrity": "sha512-eXTggHWSooYhq49F2opQhuHWgzucfF2YgODK4e1566GQs5BIfP30B0oenwBJHfWxAs2fyPB1s7Mg949zLf61Yw==", + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/sibiraj-s" + } + ], + "engines": { + "node": ">=8" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/jest-worker": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", + "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", + "dependencies": { + "@types/node": "*", + "merge-stream": "^2.0.0", + "supports-color": "^8.0.0" + }, + "engines": { + "node": ">= 10.13.0" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/jest-worker/node_modules/supports-color": { + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", + "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/supports-color?sponsor=1" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro/-/metro-0.76.7.tgz", + "integrity": "sha512-67ZGwDeumEPnrHI+pEDSKH2cx+C81Gx8Mn5qOtmGUPm/Up9Y4I1H2dJZ5n17MWzejNo0XAvPh0QL0CrlJEODVQ==", + "dependencies": { + "@babel/code-frame": "^7.0.0", + "@babel/core": "^7.20.0", + "@babel/generator": "^7.20.0", + "@babel/parser": "^7.20.0", + "@babel/template": "^7.0.0", + "@babel/traverse": "^7.20.0", + "@babel/types": "^7.20.0", + "accepts": "^1.3.7", + "async": "^3.2.2", + "chalk": "^4.0.0", + "ci-info": "^2.0.0", + "connect": "^3.6.5", + "debug": "^2.2.0", + "denodeify": "^1.2.1", + "error-stack-parser": "^2.0.6", + "graceful-fs": "^4.2.4", + "hermes-parser": "0.12.0", + "image-size": "^1.0.2", + "invariant": "^2.2.4", + "jest-worker": "^27.2.0", + "jsc-safe-url": "^0.2.2", + "lodash.throttle": "^4.1.1", + "metro-babel-transformer": "0.76.7", + "metro-cache": "0.76.7", + "metro-cache-key": "0.76.7", + "metro-config": "0.76.7", + "metro-core": "0.76.7", + "metro-file-map": "0.76.7", + "metro-inspector-proxy": "0.76.7", + "metro-minify-terser": "0.76.7", + "metro-minify-uglify": "0.76.7", + "metro-react-native-babel-preset": "0.76.7", + "metro-resolver": "0.76.7", + "metro-runtime": "0.76.7", + "metro-source-map": "0.76.7", + "metro-symbolicate": "0.76.7", + "metro-transform-plugins": "0.76.7", + "metro-transform-worker": "0.76.7", + "mime-types": "^2.1.27", + "node-fetch": "^2.2.0", + "nullthrows": "^1.1.1", + "rimraf": "^3.0.2", + "serialize-error": "^2.1.0", + "source-map": "^0.5.6", + "strip-ansi": "^6.0.0", + "throat": "^5.0.0", + "ws": "^7.5.1", + "yargs": "^17.6.2" + }, + "bin": { + "metro": "src/cli.js" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-babel-transformer": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-babel-transformer/-/metro-babel-transformer-0.76.7.tgz", + "integrity": "sha512-bgr2OFn0J4r0qoZcHrwEvccF7g9k3wdgTOgk6gmGHrtlZ1Jn3oCpklW/DfZ9PzHfjY2mQammKTc19g/EFGyOJw==", + "dependencies": { + "@babel/core": "^7.20.0", + "hermes-parser": "0.12.0", + "nullthrows": "^1.1.1" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-cache": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-cache/-/metro-cache-0.76.7.tgz", + "integrity": "sha512-nWBMztrs5RuSxZRI7hgFgob5PhYDmxICh9FF8anm9/ito0u0vpPvRxt7sRu8fyeD2AHdXqE7kX32rWY0LiXgeg==", + "dependencies": { + "metro-core": "0.76.7", + "rimraf": "^3.0.2" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-cache-key": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-cache-key/-/metro-cache-key-0.76.7.tgz", + "integrity": "sha512-0pecoIzwsD/Whn/Qfa+SDMX2YyasV0ndbcgUFx7w1Ct2sLHClujdhQ4ik6mvQmsaOcnGkIyN0zcceMDjC2+BFQ==", + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-config": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-config/-/metro-config-0.76.7.tgz", + "integrity": "sha512-CFDyNb9bqxZemiChC/gNdXZ7OQkIwmXzkrEXivcXGbgzlt/b2juCv555GWJHyZSlorwnwJfY3uzAFu4A9iRVfg==", + "dependencies": { + "connect": "^3.6.5", + "cosmiconfig": "^5.0.5", + "jest-validate": "^29.2.1", + "metro": "0.76.7", + "metro-cache": "0.76.7", + "metro-core": "0.76.7", + "metro-runtime": "0.76.7" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-core": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-core/-/metro-core-0.76.7.tgz", + "integrity": "sha512-0b8KfrwPmwCMW+1V7ZQPkTy2tsEKZjYG9Pu1PTsu463Z9fxX7WaR0fcHFshv+J1CnQSUTwIGGjbNvj1teKe+pw==", + "dependencies": { + "lodash.throttle": "^4.1.1", + "metro-resolver": "0.76.7" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-file-map": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-file-map/-/metro-file-map-0.76.7.tgz", + "integrity": "sha512-s+zEkTcJ4mOJTgEE2ht4jIo1DZfeWreQR3tpT3gDV/Y/0UQ8aJBTv62dE775z0GLsWZApiblAYZsj7ZE8P06nw==", + "dependencies": { + "anymatch": "^3.0.3", + "debug": "^2.2.0", + "fb-watchman": "^2.0.0", + "graceful-fs": "^4.2.4", + "invariant": "^2.2.4", + "jest-regex-util": "^27.0.6", + "jest-util": "^27.2.0", + "jest-worker": "^27.2.0", + "micromatch": "^4.0.4", + "node-abort-controller": "^3.1.1", + "nullthrows": "^1.1.1", + "walker": "^1.0.7" + }, + "engines": { + "node": ">=16" + }, + "optionalDependencies": { + "fsevents": "^2.3.2" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-inspector-proxy": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-inspector-proxy/-/metro-inspector-proxy-0.76.7.tgz", + "integrity": "sha512-rNZ/6edTl/1qUekAhAbaFjczMphM50/UjtxiKulo6vqvgn/Mjd9hVqDvVYfAMZXqPvlusD88n38UjVYPkruLSg==", + "dependencies": { + "connect": "^3.6.5", + "debug": "^2.2.0", + "node-fetch": "^2.2.0", + "ws": "^7.5.1", + "yargs": "^17.6.2" + }, + "bin": { + "metro-inspector-proxy": "src/cli.js" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-minify-terser": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-minify-terser/-/metro-minify-terser-0.76.7.tgz", + "integrity": "sha512-FQiZGhIxCzhDwK4LxyPMLlq0Tsmla10X7BfNGlYFK0A5IsaVKNJbETyTzhpIwc+YFRT4GkFFwgo0V2N5vxO5HA==", + "dependencies": { + "terser": "^5.15.0" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-minify-uglify": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-minify-uglify/-/metro-minify-uglify-0.76.7.tgz", + "integrity": "sha512-FuXIU3j2uNcSvQtPrAJjYWHruPiQ+EpE++J9Z+VznQKEHcIxMMoQZAfIF2IpZSrZYfLOjVFyGMvj41jQMxV1Vw==", + "dependencies": { + "uglify-es": "^3.1.9" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-react-native-babel-preset": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-react-native-babel-preset/-/metro-react-native-babel-preset-0.76.7.tgz", + "integrity": "sha512-R25wq+VOSorAK3hc07NW0SmN8z9S/IR0Us0oGAsBcMZnsgkbOxu77Mduqf+f4is/wnWHc5+9bfiqdLnaMngiVw==", + "dependencies": { + "@babel/core": "^7.20.0", + "@babel/plugin-proposal-async-generator-functions": "^7.0.0", + "@babel/plugin-proposal-class-properties": "^7.18.0", + "@babel/plugin-proposal-export-default-from": "^7.0.0", + "@babel/plugin-proposal-nullish-coalescing-operator": "^7.18.0", + "@babel/plugin-proposal-numeric-separator": "^7.0.0", + "@babel/plugin-proposal-object-rest-spread": "^7.20.0", + "@babel/plugin-proposal-optional-catch-binding": "^7.0.0", + "@babel/plugin-proposal-optional-chaining": "^7.20.0", + "@babel/plugin-syntax-dynamic-import": "^7.8.0", + "@babel/plugin-syntax-export-default-from": "^7.0.0", + "@babel/plugin-syntax-flow": "^7.18.0", + "@babel/plugin-syntax-nullish-coalescing-operator": "^7.0.0", + "@babel/plugin-syntax-optional-chaining": "^7.0.0", + "@babel/plugin-transform-arrow-functions": "^7.0.0", + "@babel/plugin-transform-async-to-generator": "^7.20.0", + "@babel/plugin-transform-block-scoping": "^7.0.0", + "@babel/plugin-transform-classes": "^7.0.0", + "@babel/plugin-transform-computed-properties": "^7.0.0", + "@babel/plugin-transform-destructuring": "^7.20.0", + "@babel/plugin-transform-flow-strip-types": "^7.20.0", + "@babel/plugin-transform-function-name": "^7.0.0", + "@babel/plugin-transform-literals": "^7.0.0", + "@babel/plugin-transform-modules-commonjs": "^7.0.0", + "@babel/plugin-transform-named-capturing-groups-regex": "^7.0.0", + "@babel/plugin-transform-parameters": "^7.0.0", + "@babel/plugin-transform-react-display-name": "^7.0.0", + "@babel/plugin-transform-react-jsx": "^7.0.0", + "@babel/plugin-transform-react-jsx-self": "^7.0.0", + "@babel/plugin-transform-react-jsx-source": "^7.0.0", + "@babel/plugin-transform-runtime": "^7.0.0", + "@babel/plugin-transform-shorthand-properties": "^7.0.0", + "@babel/plugin-transform-spread": "^7.0.0", + "@babel/plugin-transform-sticky-regex": "^7.0.0", + "@babel/plugin-transform-typescript": "^7.5.0", + "@babel/plugin-transform-unicode-regex": "^7.0.0", + "@babel/template": "^7.0.0", + "babel-plugin-transform-flow-enums": "^0.0.2", + "react-refresh": "^0.4.0" + }, + "engines": { + "node": ">=16" + }, + "peerDependencies": { + "@babel/core": "*" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-react-native-babel-transformer": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-react-native-babel-transformer/-/metro-react-native-babel-transformer-0.76.7.tgz", + "integrity": "sha512-W6lW3J7y/05ph3c2p3KKJNhH0IdyxdOCbQ5it7aM2MAl0SM4wgKjaV6EYv9b3rHklpV6K3qMH37UKVcjMooWiA==", + "dependencies": { + "@babel/core": "^7.20.0", + "babel-preset-fbjs": "^3.4.0", + "hermes-parser": "0.12.0", + "metro-react-native-babel-preset": "0.76.7", + "nullthrows": "^1.1.1" + }, + "engines": { + "node": ">=16" + }, + "peerDependencies": { + "@babel/core": "*" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-resolver": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-resolver/-/metro-resolver-0.76.7.tgz", + "integrity": "sha512-pC0Wgq29HHIHrwz23xxiNgylhI8Rq1V01kQaJ9Kz11zWrIdlrH0ZdnJ7GC6qA0ErROG+cXmJ0rJb8/SW1Zp2IA==", + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-runtime": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-runtime/-/metro-runtime-0.76.7.tgz", + "integrity": "sha512-MuWHubQHymUWBpZLwuKZQgA/qbb35WnDAKPo83rk7JRLIFPvzXSvFaC18voPuzJBt1V98lKQIonh6MiC9gd8Ug==", + "dependencies": { + "@babel/runtime": "^7.0.0", + "react-refresh": "^0.4.0" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-source-map": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-source-map/-/metro-source-map-0.76.7.tgz", + "integrity": "sha512-Prhx7PeRV1LuogT0Kn5VjCuFu9fVD68eefntdWabrksmNY6mXK8pRqzvNJOhTojh6nek+RxBzZeD6MIOOyXS6w==", + "dependencies": { + "@babel/traverse": "^7.20.0", + "@babel/types": "^7.20.0", + "invariant": "^2.2.4", + "metro-symbolicate": "0.76.7", + "nullthrows": "^1.1.1", + "ob1": "0.76.7", + "source-map": "^0.5.6", + "vlq": "^1.0.0" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-symbolicate": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-symbolicate/-/metro-symbolicate-0.76.7.tgz", + "integrity": "sha512-p0zWEME5qLSL1bJb93iq+zt5fz3sfVn9xFYzca1TJIpY5MommEaS64Va87lp56O0sfEIvh4307Oaf/ZzRjuLiQ==", + "dependencies": { + "invariant": "^2.2.4", + "metro-source-map": "0.76.7", + "nullthrows": "^1.1.1", + "source-map": "^0.5.6", + "through2": "^2.0.1", + "vlq": "^1.0.0" + }, + "bin": { + "metro-symbolicate": "src/index.js" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-transform-plugins": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-transform-plugins/-/metro-transform-plugins-0.76.7.tgz", + "integrity": "sha512-iSmnjVApbdivjuzb88Orb0JHvcEt5veVyFAzxiS5h0QB+zV79w6JCSqZlHCrbNOkOKBED//LqtKbFVakxllnNg==", + "dependencies": { + "@babel/core": "^7.20.0", + "@babel/generator": "^7.20.0", + "@babel/template": "^7.0.0", + "@babel/traverse": "^7.20.0", + "nullthrows": "^1.1.1" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/metro-transform-worker": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-transform-worker/-/metro-transform-worker-0.76.7.tgz", + "integrity": "sha512-cGvELqFMVk9XTC15CMVzrCzcO6sO1lURfcbgjuuPdzaWuD11eEyocvkTX0DPiRjsvgAmicz4XYxVzgYl3MykDw==", + "dependencies": { + "@babel/core": "^7.20.0", + "@babel/generator": "^7.20.0", + "@babel/parser": "^7.20.0", + "@babel/types": "^7.20.0", + "babel-preset-fbjs": "^3.4.0", + "metro": "0.76.7", + "metro-babel-transformer": "0.76.7", + "metro-cache": "0.76.7", + "metro-cache-key": "0.76.7", + "metro-source-map": "0.76.7", + "metro-transform-plugins": "0.76.7", + "nullthrows": "^1.1.1" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/ob1": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/ob1/-/ob1-0.76.7.tgz", + "integrity": "sha512-BQdRtxxoUNfSoZxqeBGOyuT9nEYSn18xZHwGMb0mMVpn2NBcYbnyKY4BK2LIHRgw33CBGlUmE+KMaNvyTpLLtQ==", + "engines": { + "node": ">=16" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/parse-json": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", + "integrity": "sha512-aOIos8bujGN93/8Ox/jPLh7RwVnPEysynVFE+fQZyg6jKELEHwzgKdLRFHUgXJL6kylijVSBC4BvN9OmsB48Rw==", + "dependencies": { + "error-ex": "^1.3.1", + "json-parse-better-errors": "^1.0.1" + }, + "engines": { + "node": ">=4" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/react-refresh": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/react-refresh/-/react-refresh-0.4.3.tgz", + "integrity": "sha512-Hwln1VNuGl/6bVwnd0Xdn1e84gT/8T9aYNL+HAKDArLCS7LWjwr7StE30IEYbIkx0Vi3vs+coQxe+SQDbGbbpA==", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/resolve-from": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-3.0.0.tgz", + "integrity": "sha512-GnlH6vxLymXJNMBo7XP1fJIzBFbdYt49CuTwmB/6N53t+kMPRMFKz783LlQ4tv28XoQfMWinAJX6WCGf2IlaIw==", + "engines": { + "node": ">=4" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/serialize-error": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/serialize-error/-/serialize-error-2.1.0.tgz", + "integrity": "sha512-ghgmKt5o4Tly5yEG/UJp8qTd0AN7Xalw4XBtDEKP655B699qMEtra1WlXeE6WIvdEG481JvRxULKsInq/iNysw==", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha512-LbrmJOMUSdEVxIKvdcJzQC+nQhe8FUZQTXQy6+I75skNgn3OoQ0DZA8YnFa7gp8tqtL3KPf1kmo0R5DoApeSGQ==", + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/@react-native-community/cli-plugin-metro/node_modules/supports-color": { "version": "7.2.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", @@ -7390,13 +7932,66 @@ "node": ">=8" } }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/ws": { + "version": "7.5.9", + "resolved": "https://registry.npmjs.org/ws/-/ws-7.5.9.tgz", + "integrity": "sha512-F+P9Jil7UiSKSkppIiD94dN07AwvFixvLIj1Og1Rl9GGMuNipJnV9JzjD6XuqmAeiswGvUmNLjr5cFuXwNS77Q==", + "engines": { + "node": ">=8.3.0" + }, + "peerDependencies": { + "bufferutil": "^4.0.1", + "utf-8-validate": "^5.0.2" + }, + "peerDependenciesMeta": { + "bufferutil": { + "optional": true + }, + "utf-8-validate": { + "optional": true + } + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/y18n": { + "version": "5.0.8", + "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", + "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==", + "engines": { + "node": ">=10" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/yargs": { + "version": "17.7.2", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", + "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", + "dependencies": { + "cliui": "^8.0.1", + "escalade": "^3.1.1", + "get-caller-file": "^2.0.5", + "require-directory": "^2.1.1", + "string-width": "^4.2.3", + "y18n": "^5.0.5", + "yargs-parser": "^21.1.1" + }, + "engines": { + "node": ">=12" + } + }, + "node_modules/@react-native-community/cli-plugin-metro/node_modules/yargs-parser": { + "version": "21.1.1", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz", + "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==", + "engines": { + "node": ">=12" + } + }, "node_modules/@react-native-community/cli-server-api": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-server-api/-/cli-server-api-11.3.5.tgz", - "integrity": "sha512-PM/jF13uD1eAKuC84lntNuM5ZvJAtyb+H896P1dBIXa9boPLa3KejfUvNVoyOUJ5s8Ht25JKbc3yieV2+GMBDA==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-server-api/-/cli-server-api-11.3.6.tgz", + "integrity": "sha512-8GUKodPnURGtJ9JKg8yOHIRtWepPciI3ssXVw5jik7+dZ43yN8P5BqCoDaq8e1H1yRer27iiOfT7XVnwk8Dueg==", "dependencies": { - "@react-native-community/cli-debugger-ui": "11.3.5", - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-debugger-ui": "11.3.6", + "@react-native-community/cli-tools": "11.3.6", "compression": "^1.7.1", "connect": "^3.6.5", "errorhandler": "^1.5.1", @@ -7484,9 +8079,9 @@ } }, "node_modules/@react-native-community/cli-tools": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-tools/-/cli-tools-11.3.5.tgz", - "integrity": "sha512-zDklE1+ah/zL4BLxut5XbzqCj9KTHzbYBKX7//cXw2/0TpkNCaY9c+iKx//gZ5m7U1OKbb86Fm2b0AKtKVRf6Q==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-tools/-/cli-tools-11.3.6.tgz", + "integrity": "sha512-JpmUTcDwAGiTzLsfMlIAYpCMSJ9w2Qlf7PU7mZIRyEu61UzEawyw83DkqfbzDPBuRwRnaeN44JX2CP/yTO3ThQ==", "dependencies": { "appdirsjs": "^1.2.4", "chalk": "^4.1.2", @@ -7495,7 +8090,7 @@ "node-fetch": "^2.6.0", "open": "^6.2.0", "ora": "^5.4.1", - "semver": "^6.3.0", + "semver": "^7.5.2", "shell-quote": "^1.7.3" } }, @@ -7571,14 +8166,6 @@ "node": ">=8" } }, - "node_modules/@react-native-community/cli-tools/node_modules/semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", - "bin": { - "semver": "bin/semver.js" - } - }, "node_modules/@react-native-community/cli-tools/node_modules/supports-color": { "version": "7.2.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", @@ -7591,9 +8178,9 @@ } }, "node_modules/@react-native-community/cli-types": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-types/-/cli-types-11.3.5.tgz", - "integrity": "sha512-pf0kdWMEfPSV/+8rcViDCFzbLMtWIHMZ8ay7hKwqaoWegsJ0oprSF2tSTH+LSC/7X1Beb9ssIvHj1m5C4es5Xg==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-types/-/cli-types-11.3.6.tgz", + "integrity": "sha512-6DxjrMKx5x68N/tCJYVYRKAtlRHbtUVBZrnAvkxbRWFD9v4vhNgsPM0RQm8i2vRugeksnao5mbnRGpS6c0awCw==", "dependencies": { "joi": "^17.2.1" } @@ -7736,14 +8323,6 @@ "node": ">=8" } }, - "node_modules/@react-native-community/cli/node_modules/semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==", - "bin": { - "semver": "bin/semver.js" - } - }, "node_modules/@react-native-community/cli/node_modules/supports-color": { "version": "7.2.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", @@ -7990,15 +8569,15 @@ "license": "MIT" }, "node_modules/@react-native/metro-config": { - "version": "0.72.9", - "resolved": "https://registry.npmjs.org/@react-native/metro-config/-/metro-config-0.72.9.tgz", - "integrity": "sha512-5MGmyDnXPeprRuvgPGE4LZ+e+ovofSd5YY6nFDwg6wbjRGOkeCRRlaTlQT+fjmv+zr4vYG+MUTKBlaO+fui/vA==", + "version": "0.72.11", + "resolved": "https://registry.npmjs.org/@react-native/metro-config/-/metro-config-0.72.11.tgz", + "integrity": "sha512-661EyQnDdVelyc0qP/ew7kKkGAh6N6KlkuPLC2SQ8sxaXskVU6fSuNlpLW4bUTBUDFKG8gEOU2hp6rzk4wQnGQ==", "dev": true, "dependencies": { "@react-native/js-polyfills": "^0.72.1", - "metro-config": "0.76.7", - "metro-react-native-babel-transformer": "0.76.7", - "metro-runtime": "0.76.7" + "metro-config": "0.76.8", + "metro-react-native-babel-transformer": "0.76.8", + "metro-runtime": "0.76.8" } }, "node_modules/@react-native/normalize-color": { @@ -8011,9 +8590,9 @@ "integrity": "sha512-285lfdqSXaqKuBbbtP9qL2tDrfxdOFtIMvkKadtleRQkdOxx+uzGvFr82KHmc/sSiMtfXGp7JnFYWVh4sFl7Yw==" }, "node_modules/@react-native/virtualized-lists": { - "version": "0.72.6", - "resolved": "https://registry.npmjs.org/@react-native/virtualized-lists/-/virtualized-lists-0.72.6.tgz", - "integrity": "sha512-JhT6ydu35LvbSKdwnhWDuGHMOwM0WAh9oza/X8vXHA8ELHRyQ/4p8eKz/bTQcbQziJaaleUURToGhFuCtgiMoA==", + "version": "0.72.8", + "resolved": "https://registry.npmjs.org/@react-native/virtualized-lists/-/virtualized-lists-0.72.8.tgz", + "integrity": "sha512-J3Q4Bkuo99k7mu+jPS9gSUSgq+lLRSI/+ahXNwV92XgJ/8UgOTxu2LPwhJnBk/sQKxq7E8WkZBnBiozukQMqrw==", "dependencies": { "invariant": "^2.2.4", "nullthrows": "^1.1.1" @@ -21038,7 +21617,8 @@ }, "node_modules/babel-plugin-syntax-trailing-function-commas": { "version": "7.0.0-beta.0", - "license": "MIT" + "resolved": "https://registry.npmjs.org/babel-plugin-syntax-trailing-function-commas/-/babel-plugin-syntax-trailing-function-commas-7.0.0-beta.0.tgz", + "integrity": "sha512-Xj9XuRuz3nTSbaTXWv3itLOcxyF4oPD8douBBmj7U9BBC6nEBYfyOJYQMf/8PJAFotC62UY5dFfIGEPr7WswzQ==" }, "node_modules/babel-plugin-transform-class-properties": { "version": "6.24.1", @@ -21104,7 +21684,8 @@ }, "node_modules/babel-preset-fbjs": { "version": "3.4.0", - "license": "MIT", + "resolved": "https://registry.npmjs.org/babel-preset-fbjs/-/babel-preset-fbjs-3.4.0.tgz", + "integrity": "sha512-9ywCsCvo1ojrw0b+XYk7aFvTH6D9064t0RIL1rtMf3nsa02Xw41MS7sZw216Im35xj/UY0PDBQsa1brUDDF1Ow==", "dependencies": { "@babel/plugin-proposal-class-properties": "^7.0.0", "@babel/plugin-proposal-object-rest-spread": "^7.0.0", @@ -22669,9 +23250,9 @@ } }, "node_modules/cli-spinners": { - "version": "2.9.0", - "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-2.9.0.tgz", - "integrity": "sha512-4/aL9X3Wh0yiMQlE+eeRhWP6vclO3QRtw1JHKIT0FFUs5FjpFmESqtMvYZ0+lbzBw900b95mS0hohy+qn2VK/g==", + "version": "2.9.1", + "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-2.9.1.tgz", + "integrity": "sha512-jHgecW0pxkonBJdrKsqxgRX9AcG+u/5k0Q7WPDfi8AogLAdwxEkyYYNWwZ5GvVFoFx2uiY1eNcSK00fh+1+FyQ==", "engines": { "node": ">=6" }, @@ -23138,7 +23719,8 @@ }, "node_modules/connect": { "version": "3.7.0", - "license": "MIT", + "resolved": "https://registry.npmjs.org/connect/-/connect-3.7.0.tgz", + "integrity": "sha512-ZqRXc+tZukToSNmh5C2iWMSoV3X1YUcPbqEM4DkEG5tNQXrQUZCNVGGv3IuicnkMtPfGf3Xtp8WCXs295iQ1pQ==", "dependencies": { "debug": "2.6.9", "finalhandler": "1.1.2", @@ -23159,14 +23741,16 @@ }, "node_modules/connect/node_modules/debug": { "version": "2.6.9", - "license": "MIT", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", "dependencies": { "ms": "2.0.0" } }, "node_modules/connect/node_modules/finalhandler": { "version": "1.1.2", - "license": "MIT", + "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.2.tgz", + "integrity": "sha512-aAWcW57uxVNrQZqFXjITpW3sIUQmHGG3qSb9mUah9MgMC4NeWhNOlNjXEYq3HjRAvL6arUviZGGJsBg6z0zsWA==", "dependencies": { "debug": "2.6.9", "encodeurl": "~1.0.2", @@ -23182,11 +23766,13 @@ }, "node_modules/connect/node_modules/ms": { "version": "2.0.0", - "license": "MIT" + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" }, "node_modules/connect/node_modules/on-finished": { "version": "2.3.0", - "license": "MIT", + "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.3.0.tgz", + "integrity": "sha512-ikqdkGAAyf/X/gPhXGvfgAytDZtDbr+bkNUJ0N9h5MI/dmdgCs3l6hoHrcUv41sRKew3jIwrp4qQDXiK99Utww==", "dependencies": { "ee-first": "1.1.1" }, @@ -23196,7 +23782,8 @@ }, "node_modules/connect/node_modules/statuses": { "version": "1.5.0", - "license": "MIT", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", + "integrity": "sha512-OpZ3zP+jT1PI7I8nemJX4AKmAX070ZkYPVWV/AaKTJl+tXCTGyVdC1a4SL8RUQYEwk/f34ZX8UTykN68FwrqAA==", "engines": { "node": ">= 0.6" } @@ -24572,7 +25159,8 @@ }, "node_modules/denodeify": { "version": "1.2.1", - "license": "MIT" + "resolved": "https://registry.npmjs.org/denodeify/-/denodeify-1.2.1.tgz", + "integrity": "sha512-KNTihKNmQENUZeKu5fzfpzRqR5S2VMp4gl9RFHiWzj9DfvYQPMJ6XHKNaQxaGCXwPk6y9yme3aUoaiAe+KX+vg==" }, "node_modules/depd": { "version": "2.0.0", @@ -25905,9 +26493,9 @@ } }, "node_modules/eslint-config-expensify": { - "version": "2.0.38", - "resolved": "https://registry.npmjs.org/eslint-config-expensify/-/eslint-config-expensify-2.0.38.tgz", - "integrity": "sha512-jAlrYSjkDV8YESUUPcaTjUM8Fgru+37FS+Hq6zzcRR0FbA5bLiOPguhJHo77XpYh5N+PEf4wrpgsS04sjdgDPg==", + "version": "2.0.39", + "resolved": "https://registry.npmjs.org/eslint-config-expensify/-/eslint-config-expensify-2.0.39.tgz", + "integrity": "sha512-DIxR3k99ZIDPE2NK+WLLRWpoDq06gTXdY8XZg9Etd1UqZ7fXm/Yz3/QkTxu7CH7UaXbCH3P4PTo023ULQGKOSw==", "dev": true, "dependencies": { "@lwc/eslint-plugin-lwc": "^0.11.0", @@ -27519,8 +28107,8 @@ }, "node_modules/expensify-common": { "version": "1.0.0", - "resolved": "git+ssh://git@github.com/Expensify/expensify-common.git#35bff866a8d345b460ea6256f0a0f0a8a7f81086", - "integrity": "sha512-O0KbaMljSFyoZXcxtx5B2qBL+n0md3wYOrArMVT8N0W+4wKncn+p8/vrmVlUMHe/vDloUbVmUZNdHwOZNWdx3w==", + "resolved": "git+ssh://git@github.com/Expensify/expensify-common.git#1609f1848cc0c2528064519c3ea48b4953a708ee", + "integrity": "sha512-sUd/ky6xCB/mShVaD2nVkedGL2xy+h6Jf5MfX9GOiYX8wB2D8uZSpqswz515uwcp8RDWrA5wxM2cR6pBXNfgxw==", "license": "MIT", "dependencies": { "classnames": "2.3.1", @@ -33572,9 +34160,9 @@ } }, "node_modules/joi": { - "version": "17.9.2", - "resolved": "https://registry.npmjs.org/joi/-/joi-17.9.2.tgz", - "integrity": "sha512-Itk/r+V4Dx0V3c7RLFdRh12IOjySm2/WGPMubBT92cQvRfYZhPM2W0hZlctjj72iES8jsRCwp7S/cRmWBnJ4nw==", + "version": "17.10.1", + "resolved": "https://registry.npmjs.org/joi/-/joi-17.10.1.tgz", + "integrity": "sha512-vIiDxQKmRidUVp8KngT8MZSOcmRVm2zV7jbMjNYWuHcJWI0bUck3nRTGQjhpPlQenIQIBC5Vp9AhcnHbWQqafw==", "dependencies": { "@hapi/hoek": "^9.0.0", "@hapi/topo": "^5.0.0", @@ -34234,7 +34822,8 @@ }, "node_modules/lodash.throttle": { "version": "4.1.1", - "license": "MIT" + "resolved": "https://registry.npmjs.org/lodash.throttle/-/lodash.throttle-4.1.1.tgz", + "integrity": "sha512-wIkUCfVKpVsWo3JSZlc+8MB5it+2AN5W8J7YVMST30UrvcQNZ1Okbj+rbVniijTWE6FGYy4XJq/rHkas8qJMLQ==" }, "node_modules/lodash.truncate": { "version": "4.4.2", @@ -35621,9 +36210,10 @@ } }, "node_modules/metro": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro/-/metro-0.76.7.tgz", - "integrity": "sha512-67ZGwDeumEPnrHI+pEDSKH2cx+C81Gx8Mn5qOtmGUPm/Up9Y4I1H2dJZ5n17MWzejNo0XAvPh0QL0CrlJEODVQ==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro/-/metro-0.76.8.tgz", + "integrity": "sha512-oQA3gLzrrYv3qKtuWArMgHPbHu8odZOD9AoavrqSFllkPgOtmkBvNNDLCELqv5SjBfqjISNffypg+5UGG3y0pg==", + "dev": true, "dependencies": { "@babel/code-frame": "^7.0.0", "@babel/core": "^7.20.0", @@ -35647,22 +36237,22 @@ "jest-worker": "^27.2.0", "jsc-safe-url": "^0.2.2", "lodash.throttle": "^4.1.1", - "metro-babel-transformer": "0.76.7", - "metro-cache": "0.76.7", - "metro-cache-key": "0.76.7", - "metro-config": "0.76.7", - "metro-core": "0.76.7", - "metro-file-map": "0.76.7", - "metro-inspector-proxy": "0.76.7", - "metro-minify-terser": "0.76.7", - "metro-minify-uglify": "0.76.7", - "metro-react-native-babel-preset": "0.76.7", - "metro-resolver": "0.76.7", - "metro-runtime": "0.76.7", - "metro-source-map": "0.76.7", - "metro-symbolicate": "0.76.7", - "metro-transform-plugins": "0.76.7", - "metro-transform-worker": "0.76.7", + "metro-babel-transformer": "0.76.8", + "metro-cache": "0.76.8", + "metro-cache-key": "0.76.8", + "metro-config": "0.76.8", + "metro-core": "0.76.8", + "metro-file-map": "0.76.8", + "metro-inspector-proxy": "0.76.8", + "metro-minify-terser": "0.76.8", + "metro-minify-uglify": "0.76.8", + "metro-react-native-babel-preset": "0.76.8", + "metro-resolver": "0.76.8", + "metro-runtime": "0.76.8", + "metro-source-map": "0.76.8", + "metro-symbolicate": "0.76.8", + "metro-transform-plugins": "0.76.8", + "metro-transform-worker": "0.76.8", "mime-types": "^2.1.27", "node-fetch": "^2.2.0", "nullthrows": "^1.1.1", @@ -35682,9 +36272,10 @@ } }, "node_modules/metro-babel-transformer": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-babel-transformer/-/metro-babel-transformer-0.76.7.tgz", - "integrity": "sha512-bgr2OFn0J4r0qoZcHrwEvccF7g9k3wdgTOgk6gmGHrtlZ1Jn3oCpklW/DfZ9PzHfjY2mQammKTc19g/EFGyOJw==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-babel-transformer/-/metro-babel-transformer-0.76.8.tgz", + "integrity": "sha512-Hh6PW34Ug/nShlBGxkwQJSgPGAzSJ9FwQXhUImkzdsDgVu6zj5bx258J8cJVSandjNoQ8nbaHK6CaHlnbZKbyA==", + "dev": true, "dependencies": { "@babel/core": "^7.20.0", "hermes-parser": "0.12.0", @@ -35695,11 +36286,12 @@ } }, "node_modules/metro-cache": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-cache/-/metro-cache-0.76.7.tgz", - "integrity": "sha512-nWBMztrs5RuSxZRI7hgFgob5PhYDmxICh9FF8anm9/ito0u0vpPvRxt7sRu8fyeD2AHdXqE7kX32rWY0LiXgeg==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-cache/-/metro-cache-0.76.8.tgz", + "integrity": "sha512-QBJSJIVNH7Hc/Yo6br/U/qQDUpiUdRgZ2ZBJmvAbmAKp2XDzsapnMwK/3BGj8JNWJF7OLrqrYHsRsukSbUBpvQ==", + "dev": true, "dependencies": { - "metro-core": "0.76.7", + "metro-core": "0.76.8", "rimraf": "^3.0.2" }, "engines": { @@ -35707,25 +36299,27 @@ } }, "node_modules/metro-cache-key": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-cache-key/-/metro-cache-key-0.76.7.tgz", - "integrity": "sha512-0pecoIzwsD/Whn/Qfa+SDMX2YyasV0ndbcgUFx7w1Ct2sLHClujdhQ4ik6mvQmsaOcnGkIyN0zcceMDjC2+BFQ==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-cache-key/-/metro-cache-key-0.76.8.tgz", + "integrity": "sha512-buKQ5xentPig9G6T37Ww/R/bC+/V1MA5xU/D8zjnhlelsrPG6w6LtHUS61ID3zZcMZqYaELWk5UIadIdDsaaLw==", + "dev": true, "engines": { "node": ">=16" } }, "node_modules/metro-config": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-config/-/metro-config-0.76.7.tgz", - "integrity": "sha512-CFDyNb9bqxZemiChC/gNdXZ7OQkIwmXzkrEXivcXGbgzlt/b2juCv555GWJHyZSlorwnwJfY3uzAFu4A9iRVfg==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-config/-/metro-config-0.76.8.tgz", + "integrity": "sha512-SL1lfKB0qGHALcAk2zBqVgQZpazDYvYFGwCK1ikz0S6Y/CM2i2/HwuZN31kpX6z3mqjv/6KvlzaKoTb1otuSAA==", + "dev": true, "dependencies": { "connect": "^3.6.5", "cosmiconfig": "^5.0.5", "jest-validate": "^29.2.1", - "metro": "0.76.7", - "metro-cache": "0.76.7", - "metro-core": "0.76.7", - "metro-runtime": "0.76.7" + "metro": "0.76.8", + "metro-cache": "0.76.8", + "metro-core": "0.76.8", + "metro-runtime": "0.76.8" }, "engines": { "node": ">=16" @@ -35735,6 +36329,7 @@ "version": "5.2.1", "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-5.2.1.tgz", "integrity": "sha512-H65gsXo1SKjf8zmrJ67eJk8aIRKV5ff2D4uKZIBZShbhGSpEmsQOPW/SKMKYhSTrqR7ufy6RP69rPogdaPh/kA==", + "dev": true, "dependencies": { "import-fresh": "^2.0.0", "is-directory": "^0.3.1", @@ -35749,6 +36344,7 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-2.0.0.tgz", "integrity": "sha512-eZ5H8rcgYazHbKC3PG4ClHNykCSxtAhxSSEM+2mb+7evD2CKF5V7c0dNum7AdpDh0ZdICwZY9sRSn8f+KH96sg==", + "dev": true, "dependencies": { "caller-path": "^2.0.0", "resolve-from": "^3.0.0" @@ -35761,6 +36357,7 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", "integrity": "sha512-aOIos8bujGN93/8Ox/jPLh7RwVnPEysynVFE+fQZyg6jKELEHwzgKdLRFHUgXJL6kylijVSBC4BvN9OmsB48Rw==", + "dev": true, "dependencies": { "error-ex": "^1.3.1", "json-parse-better-errors": "^1.0.1" @@ -35773,26 +36370,29 @@ "version": "3.0.0", "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-3.0.0.tgz", "integrity": "sha512-GnlH6vxLymXJNMBo7XP1fJIzBFbdYt49CuTwmB/6N53t+kMPRMFKz783LlQ4tv28XoQfMWinAJX6WCGf2IlaIw==", + "dev": true, "engines": { "node": ">=4" } }, "node_modules/metro-core": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-core/-/metro-core-0.76.7.tgz", - "integrity": "sha512-0b8KfrwPmwCMW+1V7ZQPkTy2tsEKZjYG9Pu1PTsu463Z9fxX7WaR0fcHFshv+J1CnQSUTwIGGjbNvj1teKe+pw==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-core/-/metro-core-0.76.8.tgz", + "integrity": "sha512-sl2QLFI3d1b1XUUGxwzw/KbaXXU/bvFYrSKz6Sg19AdYGWFyzsgZ1VISRIDf+HWm4R/TJXluhWMEkEtZuqi3qA==", + "dev": true, "dependencies": { "lodash.throttle": "^4.1.1", - "metro-resolver": "0.76.7" + "metro-resolver": "0.76.8" }, "engines": { "node": ">=16" } }, "node_modules/metro-file-map": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-file-map/-/metro-file-map-0.76.7.tgz", - "integrity": "sha512-s+zEkTcJ4mOJTgEE2ht4jIo1DZfeWreQR3tpT3gDV/Y/0UQ8aJBTv62dE775z0GLsWZApiblAYZsj7ZE8P06nw==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-file-map/-/metro-file-map-0.76.8.tgz", + "integrity": "sha512-A/xP1YNEVwO1SUV9/YYo6/Y1MmzhL4ZnVgcJC3VmHp/BYVOXVStzgVbWv2wILe56IIMkfXU+jpXrGKKYhFyHVw==", + "dev": true, "dependencies": { "anymatch": "^3.0.3", "debug": "^2.2.0", @@ -35818,6 +36418,7 @@ "version": "27.5.1", "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dev": true, "dependencies": { "@types/istanbul-lib-coverage": "^2.0.0", "@types/istanbul-reports": "^3.0.0", @@ -35833,6 +36434,7 @@ "version": "16.0.5", "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.5.tgz", "integrity": "sha512-AxO/ADJOBFJScHbWhq2xAhlWP24rY4aCEG/NFaMvbT3X2MgRsLjhjQwsn0Zi5zn0LG9jUhCCZMeX9Dkuw6k+vQ==", + "dev": true, "dependencies": { "@types/yargs-parser": "*" } @@ -35841,6 +36443,7 @@ "version": "4.3.0", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, "dependencies": { "color-convert": "^2.0.1" }, @@ -35855,6 +36458,7 @@ "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, "dependencies": { "ansi-styles": "^4.1.0", "supports-color": "^7.1.0" @@ -35870,6 +36474,7 @@ "version": "2.0.1", "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, "dependencies": { "color-name": "~1.1.4" }, @@ -35880,12 +36485,14 @@ "node_modules/metro-file-map/node_modules/color-name": { "version": "1.1.4", "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true }, "node_modules/metro-file-map/node_modules/debug": { "version": "2.6.9", "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, "dependencies": { "ms": "2.0.0" } @@ -35894,6 +36501,7 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true, "engines": { "node": ">=8" } @@ -35902,6 +36510,7 @@ "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-regex-util/-/jest-regex-util-27.5.1.tgz", "integrity": "sha512-4bfKq2zie+x16okqDXjXn9ql2B0dScQu+vcwe4TvFVhkVyuWLqpZrZtXxLLWoXYgn0E87I6r6GRYHF7wFZBUvg==", + "dev": true, "engines": { "node": "^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0" } @@ -35910,6 +36519,7 @@ "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", + "dev": true, "dependencies": { "@jest/types": "^27.5.1", "@types/node": "*", @@ -35926,6 +36536,7 @@ "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", + "dev": true, "dependencies": { "@types/node": "*", "merge-stream": "^2.0.0", @@ -35939,6 +36550,7 @@ "version": "8.1.1", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "dev": true, "dependencies": { "has-flag": "^4.0.0" }, @@ -35952,12 +36564,14 @@ "node_modules/metro-file-map/node_modules/ms": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true }, "node_modules/metro-file-map/node_modules/supports-color": { "version": "7.2.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, "dependencies": { "has-flag": "^4.0.0" }, @@ -35966,9 +36580,10 @@ } }, "node_modules/metro-inspector-proxy": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-inspector-proxy/-/metro-inspector-proxy-0.76.7.tgz", - "integrity": "sha512-rNZ/6edTl/1qUekAhAbaFjczMphM50/UjtxiKulo6vqvgn/Mjd9hVqDvVYfAMZXqPvlusD88n38UjVYPkruLSg==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-inspector-proxy/-/metro-inspector-proxy-0.76.8.tgz", + "integrity": "sha512-Us5o5UEd4Smgn1+TfHX4LvVPoWVo9VsVMn4Ldbk0g5CQx3Gu0ygc/ei2AKPGTwsOZmKxJeACj7yMH2kgxQP/iw==", + "dev": true, "dependencies": { "connect": "^3.6.5", "debug": "^2.2.0", @@ -35987,6 +36602,7 @@ "version": "8.0.1", "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", "integrity": "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==", + "dev": true, "dependencies": { "string-width": "^4.2.0", "strip-ansi": "^6.0.1", @@ -36000,6 +36616,7 @@ "version": "2.6.9", "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, "dependencies": { "ms": "2.0.0" } @@ -36007,12 +36624,14 @@ "node_modules/metro-inspector-proxy/node_modules/ms": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true }, "node_modules/metro-inspector-proxy/node_modules/ws": { "version": "7.5.9", "resolved": "https://registry.npmjs.org/ws/-/ws-7.5.9.tgz", "integrity": "sha512-F+P9Jil7UiSKSkppIiD94dN07AwvFixvLIj1Og1Rl9GGMuNipJnV9JzjD6XuqmAeiswGvUmNLjr5cFuXwNS77Q==", + "dev": true, "engines": { "node": ">=8.3.0" }, @@ -36033,6 +36652,7 @@ "version": "5.0.8", "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==", + "dev": true, "engines": { "node": ">=10" } @@ -36041,6 +36661,7 @@ "version": "17.7.2", "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", + "dev": true, "dependencies": { "cliui": "^8.0.1", "escalade": "^3.1.1", @@ -36058,14 +36679,16 @@ "version": "21.1.1", "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz", "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==", + "dev": true, "engines": { "node": ">=12" } }, "node_modules/metro-minify-terser": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-minify-terser/-/metro-minify-terser-0.76.7.tgz", - "integrity": "sha512-FQiZGhIxCzhDwK4LxyPMLlq0Tsmla10X7BfNGlYFK0A5IsaVKNJbETyTzhpIwc+YFRT4GkFFwgo0V2N5vxO5HA==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-minify-terser/-/metro-minify-terser-0.76.8.tgz", + "integrity": "sha512-Orbvg18qXHCrSj1KbaeSDVYRy/gkro2PC7Fy2tDSH1c9RB4aH8tuMOIXnKJE+1SXxBtjWmQ5Yirwkth2DyyEZA==", + "dev": true, "dependencies": { "terser": "^5.15.0" }, @@ -36074,9 +36697,10 @@ } }, "node_modules/metro-minify-uglify": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-minify-uglify/-/metro-minify-uglify-0.76.7.tgz", - "integrity": "sha512-FuXIU3j2uNcSvQtPrAJjYWHruPiQ+EpE++J9Z+VznQKEHcIxMMoQZAfIF2IpZSrZYfLOjVFyGMvj41jQMxV1Vw==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-minify-uglify/-/metro-minify-uglify-0.76.8.tgz", + "integrity": "sha512-6l8/bEvtVaTSuhG1FqS0+Mc8lZ3Bl4RI8SeRIifVLC21eeSDp4CEBUWSGjpFyUDfi6R5dXzYaFnSgMNyfxADiQ==", + "dev": true, "dependencies": { "uglify-es": "^3.1.9" }, @@ -36085,9 +36709,10 @@ } }, "node_modules/metro-react-native-babel-preset": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-react-native-babel-preset/-/metro-react-native-babel-preset-0.76.7.tgz", - "integrity": "sha512-R25wq+VOSorAK3hc07NW0SmN8z9S/IR0Us0oGAsBcMZnsgkbOxu77Mduqf+f4is/wnWHc5+9bfiqdLnaMngiVw==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-react-native-babel-preset/-/metro-react-native-babel-preset-0.76.8.tgz", + "integrity": "sha512-Ptza08GgqzxEdK8apYsjTx2S8WDUlS2ilBlu9DR1CUcHmg4g3kOkFylZroogVAUKtpYQNYwAvdsjmrSdDNtiAg==", + "dev": true, "dependencies": { "@babel/core": "^7.20.0", "@babel/plugin-proposal-async-generator-functions": "^7.0.0", @@ -36138,20 +36763,22 @@ }, "node_modules/metro-react-native-babel-preset/node_modules/react-refresh": { "version": "0.4.3", + "dev": true, "license": "MIT", "engines": { "node": ">=0.10.0" } }, "node_modules/metro-react-native-babel-transformer": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-react-native-babel-transformer/-/metro-react-native-babel-transformer-0.76.7.tgz", - "integrity": "sha512-W6lW3J7y/05ph3c2p3KKJNhH0IdyxdOCbQ5it7aM2MAl0SM4wgKjaV6EYv9b3rHklpV6K3qMH37UKVcjMooWiA==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-react-native-babel-transformer/-/metro-react-native-babel-transformer-0.76.8.tgz", + "integrity": "sha512-3h+LfS1WG1PAzhq8QF0kfXjxuXetbY/lgz8vYMQhgrMMp17WM1DNJD0gjx8tOGYbpbBC1qesJ45KMS4o5TA73A==", + "dev": true, "dependencies": { "@babel/core": "^7.20.0", "babel-preset-fbjs": "^3.4.0", "hermes-parser": "0.12.0", - "metro-react-native-babel-preset": "0.76.7", + "metro-react-native-babel-preset": "0.76.8", "nullthrows": "^1.1.1" }, "engines": { @@ -36162,17 +36789,18 @@ } }, "node_modules/metro-resolver": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-resolver/-/metro-resolver-0.76.7.tgz", - "integrity": "sha512-pC0Wgq29HHIHrwz23xxiNgylhI8Rq1V01kQaJ9Kz11zWrIdlrH0ZdnJ7GC6qA0ErROG+cXmJ0rJb8/SW1Zp2IA==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-resolver/-/metro-resolver-0.76.8.tgz", + "integrity": "sha512-KccOqc10vrzS7ZhG2NSnL2dh3uVydarB7nOhjreQ7C4zyWuiW9XpLC4h47KtGQv3Rnv/NDLJYeDqaJ4/+140HQ==", + "dev": true, "engines": { "node": ">=16" } }, "node_modules/metro-runtime": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-runtime/-/metro-runtime-0.76.7.tgz", - "integrity": "sha512-MuWHubQHymUWBpZLwuKZQgA/qbb35WnDAKPo83rk7JRLIFPvzXSvFaC18voPuzJBt1V98lKQIonh6MiC9gd8Ug==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-runtime/-/metro-runtime-0.76.8.tgz", + "integrity": "sha512-XKahvB+iuYJSCr3QqCpROli4B4zASAYpkK+j3a0CJmokxCDNbgyI4Fp88uIL6rNaZfN0Mv35S0b99SdFXIfHjg==", "dependencies": { "@babel/runtime": "^7.0.0", "react-refresh": "^0.4.0" @@ -36190,16 +36818,16 @@ } }, "node_modules/metro-source-map": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-source-map/-/metro-source-map-0.76.7.tgz", - "integrity": "sha512-Prhx7PeRV1LuogT0Kn5VjCuFu9fVD68eefntdWabrksmNY6mXK8pRqzvNJOhTojh6nek+RxBzZeD6MIOOyXS6w==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-source-map/-/metro-source-map-0.76.8.tgz", + "integrity": "sha512-Hh0ncPsHPVf6wXQSqJqB3K9Zbudht4aUtNpNXYXSxH+pteWqGAXnjtPsRAnCsCWl38wL0jYF0rJDdMajUI3BDw==", "dependencies": { "@babel/traverse": "^7.20.0", "@babel/types": "^7.20.0", "invariant": "^2.2.4", - "metro-symbolicate": "0.76.7", + "metro-symbolicate": "0.76.8", "nullthrows": "^1.1.1", - "ob1": "0.76.7", + "ob1": "0.76.8", "source-map": "^0.5.6", "vlq": "^1.0.0" }, @@ -36216,12 +36844,12 @@ } }, "node_modules/metro-symbolicate": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-symbolicate/-/metro-symbolicate-0.76.7.tgz", - "integrity": "sha512-p0zWEME5qLSL1bJb93iq+zt5fz3sfVn9xFYzca1TJIpY5MommEaS64Va87lp56O0sfEIvh4307Oaf/ZzRjuLiQ==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-symbolicate/-/metro-symbolicate-0.76.8.tgz", + "integrity": "sha512-LrRL3uy2VkzrIXVlxoPtqb40J6Bf1mlPNmUQewipc3qfKKFgtPHBackqDy1YL0njDsWopCKcfGtFYLn0PTUn3w==", "dependencies": { "invariant": "^2.2.4", - "metro-source-map": "0.76.7", + "metro-source-map": "0.76.8", "nullthrows": "^1.1.1", "source-map": "^0.5.6", "through2": "^2.0.1", @@ -36243,9 +36871,10 @@ } }, "node_modules/metro-transform-plugins": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-transform-plugins/-/metro-transform-plugins-0.76.7.tgz", - "integrity": "sha512-iSmnjVApbdivjuzb88Orb0JHvcEt5veVyFAzxiS5h0QB+zV79w6JCSqZlHCrbNOkOKBED//LqtKbFVakxllnNg==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-transform-plugins/-/metro-transform-plugins-0.76.8.tgz", + "integrity": "sha512-PlkGTQNqS51Bx4vuufSQCdSn2R2rt7korzngo+b5GCkeX5pjinPjnO2kNhQ8l+5bO0iUD/WZ9nsM2PGGKIkWFA==", + "dev": true, "dependencies": { "@babel/core": "^7.20.0", "@babel/generator": "^7.20.0", @@ -36258,21 +36887,22 @@ } }, "node_modules/metro-transform-worker": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-transform-worker/-/metro-transform-worker-0.76.7.tgz", - "integrity": "sha512-cGvELqFMVk9XTC15CMVzrCzcO6sO1lURfcbgjuuPdzaWuD11eEyocvkTX0DPiRjsvgAmicz4XYxVzgYl3MykDw==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-transform-worker/-/metro-transform-worker-0.76.8.tgz", + "integrity": "sha512-mE1fxVAnJKmwwJyDtThildxxos9+DGs9+vTrx2ktSFMEVTtXS/bIv2W6hux1pqivqAfyJpTeACXHk5u2DgGvIQ==", + "dev": true, "dependencies": { "@babel/core": "^7.20.0", "@babel/generator": "^7.20.0", "@babel/parser": "^7.20.0", "@babel/types": "^7.20.0", "babel-preset-fbjs": "^3.4.0", - "metro": "0.76.7", - "metro-babel-transformer": "0.76.7", - "metro-cache": "0.76.7", - "metro-cache-key": "0.76.7", - "metro-source-map": "0.76.7", - "metro-transform-plugins": "0.76.7", + "metro": "0.76.8", + "metro-babel-transformer": "0.76.8", + "metro-cache": "0.76.8", + "metro-cache-key": "0.76.8", + "metro-source-map": "0.76.8", + "metro-transform-plugins": "0.76.8", "nullthrows": "^1.1.1" }, "engines": { @@ -36283,6 +36913,7 @@ "version": "4.3.0", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, "dependencies": { "color-convert": "^2.0.1" }, @@ -36297,6 +36928,7 @@ "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, "dependencies": { "ansi-styles": "^4.1.0", "supports-color": "^7.1.0" @@ -36311,12 +36943,14 @@ "node_modules/metro/node_modules/ci-info": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-2.0.0.tgz", - "integrity": "sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==" + "integrity": "sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==", + "dev": true }, "node_modules/metro/node_modules/cliui": { "version": "8.0.1", "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", "integrity": "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==", + "dev": true, "dependencies": { "string-width": "^4.2.0", "strip-ansi": "^6.0.1", @@ -36330,6 +36964,7 @@ "version": "2.0.1", "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, "dependencies": { "color-name": "~1.1.4" }, @@ -36340,12 +36975,14 @@ "node_modules/metro/node_modules/color-name": { "version": "1.1.4", "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true }, "node_modules/metro/node_modules/debug": { "version": "2.6.9", "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, "dependencies": { "ms": "2.0.0" } @@ -36354,6 +36991,7 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true, "engines": { "node": ">=8" } @@ -36362,6 +37000,7 @@ "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", + "dev": true, "dependencies": { "@types/node": "*", "merge-stream": "^2.0.0", @@ -36375,6 +37014,7 @@ "version": "8.1.1", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "dev": true, "dependencies": { "has-flag": "^4.0.0" }, @@ -36388,12 +37028,14 @@ "node_modules/metro/node_modules/ms": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true }, "node_modules/metro/node_modules/serialize-error": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/serialize-error/-/serialize-error-2.1.0.tgz", "integrity": "sha512-ghgmKt5o4Tly5yEG/UJp8qTd0AN7Xalw4XBtDEKP655B699qMEtra1WlXeE6WIvdEG481JvRxULKsInq/iNysw==", + "dev": true, "engines": { "node": ">=0.10.0" } @@ -36402,6 +37044,7 @@ "version": "0.5.7", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", "integrity": "sha512-LbrmJOMUSdEVxIKvdcJzQC+nQhe8FUZQTXQy6+I75skNgn3OoQ0DZA8YnFa7gp8tqtL3KPf1kmo0R5DoApeSGQ==", + "dev": true, "engines": { "node": ">=0.10.0" } @@ -36410,6 +37053,7 @@ "version": "7.2.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, "dependencies": { "has-flag": "^4.0.0" }, @@ -36421,6 +37065,7 @@ "version": "7.5.9", "resolved": "https://registry.npmjs.org/ws/-/ws-7.5.9.tgz", "integrity": "sha512-F+P9Jil7UiSKSkppIiD94dN07AwvFixvLIj1Og1Rl9GGMuNipJnV9JzjD6XuqmAeiswGvUmNLjr5cFuXwNS77Q==", + "dev": true, "engines": { "node": ">=8.3.0" }, @@ -36441,6 +37086,7 @@ "version": "5.0.8", "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==", + "dev": true, "engines": { "node": ">=10" } @@ -36449,6 +37095,7 @@ "version": "17.7.2", "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", + "dev": true, "dependencies": { "cliui": "^8.0.1", "escalade": "^3.1.1", @@ -36466,6 +37113,7 @@ "version": "21.1.1", "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz", "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==", + "dev": true, "engines": { "node": ">=12" } @@ -38008,9 +38656,9 @@ "license": "MIT" }, "node_modules/ob1": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/ob1/-/ob1-0.76.7.tgz", - "integrity": "sha512-BQdRtxxoUNfSoZxqeBGOyuT9nEYSn18xZHwGMb0mMVpn2NBcYbnyKY4BK2LIHRgw33CBGlUmE+KMaNvyTpLLtQ==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/ob1/-/ob1-0.76.8.tgz", + "integrity": "sha512-dlBkJJV5M/msj9KYA9upc+nUWVwuOFFTbu28X6kZeGwcuW+JxaHSBZ70SYQnk5M+j5JbNLR6yKHmgW4M5E7X5g==", "engines": { "node": ">=16" } @@ -40246,20 +40894,20 @@ } }, "node_modules/react-native": { - "version": "0.72.3", - "resolved": "https://registry.npmjs.org/react-native/-/react-native-0.72.3.tgz", - "integrity": "sha512-QqISi+JVmCssNP2FlQ4MWhlc4O/I00MRE1/GClvyZ8h/6kdsyk/sOirkYdZqX3+DrJfI3q+OnyMnsyaXIQ/5tQ==", + "version": "0.72.4", + "resolved": "https://registry.npmjs.org/react-native/-/react-native-0.72.4.tgz", + "integrity": "sha512-+vrObi0wZR+NeqL09KihAAdVlQ9IdplwznJWtYrjnQ4UbCW6rkzZJebRsugwUneSOKNFaHFEo1uKU89HsgtYBg==", "dependencies": { "@jest/create-cache-key-function": "^29.2.1", - "@react-native-community/cli": "11.3.5", - "@react-native-community/cli-platform-android": "11.3.5", - "@react-native-community/cli-platform-ios": "11.3.5", + "@react-native-community/cli": "11.3.6", + "@react-native-community/cli-platform-android": "11.3.6", + "@react-native-community/cli-platform-ios": "11.3.6", "@react-native/assets-registry": "^0.72.0", "@react-native/codegen": "^0.72.6", "@react-native/gradle-plugin": "^0.72.11", "@react-native/js-polyfills": "^0.72.1", "@react-native/normalize-colors": "^0.72.0", - "@react-native/virtualized-lists": "^0.72.6", + "@react-native/virtualized-lists": "^0.72.8", "abort-controller": "^3.0.0", "anser": "^1.4.9", "base64-js": "^1.1.2", @@ -40270,8 +40918,8 @@ "jest-environment-node": "^29.2.1", "jsc-android": "^250231.0.0", "memoize-one": "^5.0.0", - "metro-runtime": "0.76.7", - "metro-source-map": "0.76.7", + "metro-runtime": "0.76.8", + "metro-source-map": "0.76.8", "mkdirp": "^0.5.1", "nullthrows": "^1.1.1", "pretty-format": "^26.5.2", @@ -40451,8 +41099,8 @@ }, "node_modules/react-native-google-places-autocomplete": { "version": "2.5.1", - "resolved": "git+ssh://git@github.com/Expensify/react-native-google-places-autocomplete.git#ee87343c3e827ff7818abc71b6bb04fcc1f120e0", - "integrity": "sha512-OJWCz4Epj1p8tyNImWNykAqpd/X1MkNCFPY0dSbgiTJGbW4J5T4bC0PIUQ+ExjxWpWjcFaielTLdoSz0HfeIpw==", + "resolved": "git+ssh://git@github.com/Expensify/react-native-google-places-autocomplete.git#cef3ac29d9501091453136e1219e24c4ec9f9d76", + "integrity": "sha512-2z3ED8jOXasPTzBqvPwpG10LQsBArTRsYszmoz+TfqbgZrSBmP3c8rhaC//lx6Pvfs2r+KYWqJUrLf4mbCrjZw==", "license": "MIT", "dependencies": { "lodash.debounce": "^4.0.8", @@ -40556,9 +41204,9 @@ } }, "node_modules/react-native-onyx": { - "version": "1.0.77", - "resolved": "https://registry.npmjs.org/react-native-onyx/-/react-native-onyx-1.0.77.tgz", - "integrity": "sha512-HmeS1Pz/BkKNbYuhWULC9I0VRBDt8yadG0ZFIW6wuZ+VajhjD960qh7Il1+XzEBI6Vb4d7BZkPcad87ad1IEOQ==", + "version": "1.0.87", + "resolved": "https://registry.npmjs.org/react-native-onyx/-/react-native-onyx-1.0.87.tgz", + "integrity": "sha512-6mIhobSwpClDDGnJm9XEdjnpEdWfFesJ18J8Ifsb4tL6AVi+uxos5bnlZcOoMbtlUk3UozrgSyTjMfFrkD/aZA==", "dependencies": { "ascii-table": "0.0.9", "fast-equals": "^4.0.3", @@ -40571,6 +41219,7 @@ "peerDependencies": { "idb-keyval": "^6.2.1", "react": ">=18.1.0", + "react-dom": ">=18.1.0", "react-native-device-info": "^10.3.0", "react-native-performance": "^5.1.0", "react-native-quick-sqlite": "^8.0.0-beta.2" @@ -40686,9 +41335,9 @@ } }, "node_modules/react-native-reanimated": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/react-native-reanimated/-/react-native-reanimated-3.4.0.tgz", - "integrity": "sha512-B5cZJseoIkYlZTRBRN0xuU1NBxUza/6GSHhiEBQfbOufWVlUMMcWUecIRVglW49l8d2wXbfCdQlNyVoFqmHkaQ==", + "version": "3.5.4", + "resolved": "https://registry.npmjs.org/react-native-reanimated/-/react-native-reanimated-3.5.4.tgz", + "integrity": "sha512-8we9LLDO1o4Oj9/DICeEJ2K1tjfqkJagqQUglxeUAkol/HcEJ6PGxIrpBcNryLqCDYEcu6FZWld/FzizBIw6bg==", "dependencies": { "@babel/plugin-transform-object-assign": "^7.16.7", "@babel/preset-typescript": "^7.16.7", @@ -40708,7 +41357,8 @@ }, "node_modules/react-native-reanimated/node_modules/convert-source-map": { "version": "2.0.0", - "license": "MIT" + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz", + "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==" }, "node_modules/react-native-render-html": { "version": "6.3.1", @@ -45009,7 +45659,8 @@ }, "node_modules/throat": { "version": "5.0.0", - "license": "MIT" + "resolved": "https://registry.npmjs.org/throat/-/throat-5.0.0.tgz", + "integrity": "sha512-fcwX4mndzpLQKBS1DVYhGAcYaYt7vsHNIvQV+WXMvnow5cgjPphq5CaayLaGsjRdSCKZFNGt7/GYAuXaNOiYCA==" }, "node_modules/throttle-debounce": { "version": "3.0.1", @@ -46380,7 +47031,8 @@ }, "node_modules/vlq": { "version": "1.0.1", - "license": "MIT" + "resolved": "https://registry.npmjs.org/vlq/-/vlq-1.0.1.tgz", + "integrity": "sha512-gQpnTgkubC6hQgdIcRdYGDSDc+SaujOdyesZQMv6JlfQee/9Mp0Qhnys6WxDWvQnL5WZdT7o2Ul187aSt0Rq+w==" }, "node_modules/vm-browserify": { "version": "1.1.2", @@ -49126,9 +49778,11 @@ } }, "@babel/plugin-transform-object-assign": { - "version": "7.18.6", + "version": "7.22.5", + "resolved": "https://registry.npmjs.org/@babel/plugin-transform-object-assign/-/plugin-transform-object-assign-7.22.5.tgz", + "integrity": "sha512-iDhx9ARkXq4vhZ2CYOSnQXkmxkDgosLi3J8Z17mKz7LyzthtkdVchLD7WZ3aXeCuvJDOW3+1I5TpJmwIbF9MKQ==", "requires": { - "@babel/helper-plugin-utils": "^7.18.6" + "@babel/helper-plugin-utils": "^7.22.5" } }, "@babel/plugin-transform-object-rest-spread": { @@ -52504,19 +53158,19 @@ "requires": {} }, "@react-native-community/cli": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli/-/cli-11.3.5.tgz", - "integrity": "sha512-wMXgKEWe6uesw7vyXKKjx5EDRog0QdXHxdgRguG14AjQRao1+4gXEWq2yyExOTi/GDY6dfJBUGTCwGQxhnk/Lg==", - "requires": { - "@react-native-community/cli-clean": "11.3.5", - "@react-native-community/cli-config": "11.3.5", - "@react-native-community/cli-debugger-ui": "11.3.5", - "@react-native-community/cli-doctor": "11.3.5", - "@react-native-community/cli-hermes": "11.3.5", - "@react-native-community/cli-plugin-metro": "11.3.5", - "@react-native-community/cli-server-api": "11.3.5", - "@react-native-community/cli-tools": "11.3.5", - "@react-native-community/cli-types": "11.3.5", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli/-/cli-11.3.6.tgz", + "integrity": "sha512-bdwOIYTBVQ9VK34dsf6t3u6vOUU5lfdhKaAxiAVArjsr7Je88Bgs4sAbsOYsNK3tkE8G77U6wLpekknXcanlww==", + "requires": { + "@react-native-community/cli-clean": "11.3.6", + "@react-native-community/cli-config": "11.3.6", + "@react-native-community/cli-debugger-ui": "11.3.6", + "@react-native-community/cli-doctor": "11.3.6", + "@react-native-community/cli-hermes": "11.3.6", + "@react-native-community/cli-plugin-metro": "11.3.6", + "@react-native-community/cli-server-api": "11.3.6", + "@react-native-community/cli-tools": "11.3.6", + "@react-native-community/cli-types": "11.3.6", "chalk": "^4.1.2", "commander": "^9.4.1", "execa": "^5.0.0", @@ -52524,7 +53178,7 @@ "fs-extra": "^8.1.0", "graceful-fs": "^4.1.3", "prompts": "^2.4.0", - "semver": "^6.3.0" + "semver": "^7.5.2" }, "dependencies": { "ansi-styles": { @@ -52623,11 +53277,6 @@ "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", "integrity": "sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==" }, - "semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==" - }, "supports-color": { "version": "7.2.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", @@ -52644,11 +53293,11 @@ } }, "@react-native-community/cli-clean": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-clean/-/cli-clean-11.3.5.tgz", - "integrity": "sha512-1+7BU962wKkIkHRp/uW3jYbQKKGtU7L+R3g59D8K6uLccuxJYUBJv18753ojMa6SD3SAq5Xh31bAre+YwVcOTA==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-clean/-/cli-clean-11.3.6.tgz", + "integrity": "sha512-jOOaeG5ebSXTHweq1NznVJVAFKtTFWL4lWgUXl845bCGX7t1lL8xQNWHKwT8Oh1pGR2CI3cKmRjY4hBg+pEI9g==", "requires": { - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "execa": "^5.0.0", "prompts": "^2.4.0" @@ -52700,11 +53349,11 @@ } }, "@react-native-community/cli-config": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-config/-/cli-config-11.3.5.tgz", - "integrity": "sha512-fMblIsHlUleKfGsgWyjFJYfx1SqrsnhS/QXfA8w7iT6GrNOOjBp5UWx8+xlMDFcmOb9e42g1ExFDKl3n8FWkxQ==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-config/-/cli-config-11.3.6.tgz", + "integrity": "sha512-edy7fwllSFLan/6BG6/rznOBCLPrjmJAE10FzkEqNLHowi0bckiAPg1+1jlgQ2qqAxV5kuk+c9eajVfQvPLYDA==", "requires": { - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "cosmiconfig": "^5.1.0", "deepmerge": "^4.3.0", @@ -52792,22 +53441,22 @@ } }, "@react-native-community/cli-debugger-ui": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-debugger-ui/-/cli-debugger-ui-11.3.5.tgz", - "integrity": "sha512-o5JVCKEpPUXMX4r3p1cYjiy3FgdOEkezZcQ6owWEae2dYvV19lLYyJwnocm9Y7aG9PvpgI3PIMVh3KZbhS21eA==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-debugger-ui/-/cli-debugger-ui-11.3.6.tgz", + "integrity": "sha512-jhMOSN/iOlid9jn/A2/uf7HbC3u7+lGktpeGSLnHNw21iahFBzcpuO71ekEdlmTZ4zC/WyxBXw9j2ka33T358w==", "requires": { "serve-static": "^1.13.1" } }, "@react-native-community/cli-doctor": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-doctor/-/cli-doctor-11.3.5.tgz", - "integrity": "sha512-+4BuFHjoV4FFjX5y60l0s6nS0agidb1izTVwsFixeFKW73LUkOLu+Ae5HI94RAFEPE4ePEVNgYX3FynIau6K0g==", - "requires": { - "@react-native-community/cli-config": "11.3.5", - "@react-native-community/cli-platform-android": "11.3.5", - "@react-native-community/cli-platform-ios": "11.3.5", - "@react-native-community/cli-tools": "11.3.5", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-doctor/-/cli-doctor-11.3.6.tgz", + "integrity": "sha512-UT/Tt6omVPi1j6JEX+CObc85eVFghSZwy4GR9JFMsO7gNg2Tvcu1RGWlUkrbmWMAMHw127LUu6TGK66Ugu1NLA==", + "requires": { + "@react-native-community/cli-config": "11.3.6", + "@react-native-community/cli-platform-android": "11.3.6", + "@react-native-community/cli-platform-ios": "11.3.6", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "command-exists": "^1.2.8", "envinfo": "^7.7.2", @@ -52817,7 +53466,7 @@ "node-stream-zip": "^1.9.1", "ora": "^5.4.1", "prompts": "^2.4.0", - "semver": "^6.3.0", + "semver": "^7.5.2", "strip-ansi": "^5.2.0", "sudo-prompt": "^9.0.0", "wcwidth": "^1.0.1", @@ -52864,11 +53513,6 @@ "resolved": "https://registry.npmjs.org/ip/-/ip-1.1.8.tgz", "integrity": "sha512-PuExPYUiu6qMBQb4l06ecm6T6ujzhmh+MeJcW9wa89PoAz5pvd4zPgN5WJV104mb6S2T1AwNIAaB70JNrLQWhg==" }, - "semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==" - }, "strip-ansi": { "version": "5.2.0", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-5.2.0.tgz", @@ -52888,12 +53532,12 @@ } }, "@react-native-community/cli-hermes": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-hermes/-/cli-hermes-11.3.5.tgz", - "integrity": "sha512-+3m34hiaJpFel8BlJE7kJOaPzWR/8U8APZG2LXojbAdBAg99EGmQcwXIgsSVJFvH8h/nezf4DHbsPKigIe33zA==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-hermes/-/cli-hermes-11.3.6.tgz", + "integrity": "sha512-O55YAYGZ3XynpUdePPVvNuUPGPY0IJdctLAOHme73OvS80gNwfntHDXfmY70TGHWIfkK2zBhA0B+2v8s5aTyTA==", "requires": { - "@react-native-community/cli-platform-android": "11.3.5", - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-platform-android": "11.3.6", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "hermes-profile-transformer": "^0.0.6", "ip": "^1.1.5" @@ -52950,11 +53594,11 @@ } }, "@react-native-community/cli-platform-android": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-platform-android/-/cli-platform-android-11.3.5.tgz", - "integrity": "sha512-s4Lj7FKxJ/BofGi/ifjPfrA9MjFwIgYpHnHBSlqtbsvPoSYzmVCU2qlWM8fb3AmkXIwyYt4A6MEr3MmNT2UoBg==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-platform-android/-/cli-platform-android-11.3.6.tgz", + "integrity": "sha512-ZARrpLv5tn3rmhZc//IuDM1LSAdYnjUmjrp58RynlvjLDI4ZEjBAGCQmgysRgXAsK7ekMrfkZgemUczfn9td2A==", "requires": { - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "execa": "^5.0.0", "glob": "^7.1.3", @@ -53007,11 +53651,11 @@ } }, "@react-native-community/cli-platform-ios": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-platform-ios/-/cli-platform-ios-11.3.5.tgz", - "integrity": "sha512-ytJC/YCFD7P+KuQHOT5Jzh1ho2XbJEjq71yHa1gJP2PG/Q/uB4h1x2XpxDqv5iXU6E250yjvKMmkReKTW4CTig==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-platform-ios/-/cli-platform-ios-11.3.6.tgz", + "integrity": "sha512-tZ9VbXWiRW+F+fbZzpLMZlj93g3Q96HpuMsS6DRhrTiG+vMQ3o6oPWSEEmMGOvJSYU7+y68Dc9ms2liC7VD6cw==", "requires": { - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "execa": "^5.0.0", "fast-xml-parser": "^4.0.12", @@ -53065,12 +53709,12 @@ } }, "@react-native-community/cli-plugin-metro": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-plugin-metro/-/cli-plugin-metro-11.3.5.tgz", - "integrity": "sha512-r9AekfeLKdblB7LfWB71IrNy1XM03WrByQlUQajUOZAP2NmUUBLl9pMZscPjJeOSgLpHB9ixEFTIOhTabri/qg==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-plugin-metro/-/cli-plugin-metro-11.3.6.tgz", + "integrity": "sha512-D97racrPX3069ibyabJNKw9aJpVcaZrkYiEzsEnx50uauQtPDoQ1ELb/5c6CtMhAEGKoZ0B5MS23BbsSZcLs2g==", "requires": { - "@react-native-community/cli-server-api": "11.3.5", - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-server-api": "11.3.6", + "@react-native-community/cli-tools": "11.3.6", "chalk": "^4.1.2", "execa": "^5.0.0", "metro": "0.76.7", @@ -53082,6 +53726,26 @@ "readline": "^1.3.0" }, "dependencies": { + "@jest/types": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", + "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "requires": { + "@types/istanbul-lib-coverage": "^2.0.0", + "@types/istanbul-reports": "^3.0.0", + "@types/node": "*", + "@types/yargs": "^16.0.0", + "chalk": "^4.0.0" + } + }, + "@types/yargs": { + "version": "16.0.5", + "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.5.tgz", + "integrity": "sha512-AxO/ADJOBFJScHbWhq2xAhlWP24rY4aCEG/NFaMvbT3X2MgRsLjhjQwsn0Zi5zn0LG9jUhCCZMeX9Dkuw6k+vQ==", + "requires": { + "@types/yargs-parser": "*" + } + }, "ansi-styles": { "version": "4.3.0", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", @@ -53099,6 +53763,21 @@ "supports-color": "^7.1.0" } }, + "ci-info": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-2.0.0.tgz", + "integrity": "sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==" + }, + "cliui": { + "version": "8.0.1", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", + "integrity": "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==", + "requires": { + "string-width": "^4.2.0", + "strip-ansi": "^6.0.1", + "wrap-ansi": "^7.0.0" + } + }, "color-convert": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", @@ -53112,11 +53791,404 @@ "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" }, + "cosmiconfig": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-5.2.1.tgz", + "integrity": "sha512-H65gsXo1SKjf8zmrJ67eJk8aIRKV5ff2D4uKZIBZShbhGSpEmsQOPW/SKMKYhSTrqR7ufy6RP69rPogdaPh/kA==", + "requires": { + "import-fresh": "^2.0.0", + "is-directory": "^0.3.1", + "js-yaml": "^3.13.1", + "parse-json": "^4.0.0" + } + }, + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "requires": { + "ms": "2.0.0" + } + }, "has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==" }, + "import-fresh": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-2.0.0.tgz", + "integrity": "sha512-eZ5H8rcgYazHbKC3PG4ClHNykCSxtAhxSSEM+2mb+7evD2CKF5V7c0dNum7AdpDh0ZdICwZY9sRSn8f+KH96sg==", + "requires": { + "caller-path": "^2.0.0", + "resolve-from": "^3.0.0" + } + }, + "jest-regex-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-regex-util/-/jest-regex-util-27.5.1.tgz", + "integrity": "sha512-4bfKq2zie+x16okqDXjXn9ql2B0dScQu+vcwe4TvFVhkVyuWLqpZrZtXxLLWoXYgn0E87I6r6GRYHF7wFZBUvg==" + }, + "jest-util": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", + "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", + "requires": { + "@jest/types": "^27.5.1", + "@types/node": "*", + "chalk": "^4.0.0", + "ci-info": "^3.2.0", + "graceful-fs": "^4.2.9", + "picomatch": "^2.2.3" + }, + "dependencies": { + "ci-info": { + "version": "3.8.0", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-3.8.0.tgz", + "integrity": "sha512-eXTggHWSooYhq49F2opQhuHWgzucfF2YgODK4e1566GQs5BIfP30B0oenwBJHfWxAs2fyPB1s7Mg949zLf61Yw==" + } + } + }, + "jest-worker": { + "version": "27.5.1", + "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", + "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", + "requires": { + "@types/node": "*", + "merge-stream": "^2.0.0", + "supports-color": "^8.0.0" + }, + "dependencies": { + "supports-color": { + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", + "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "requires": { + "has-flag": "^4.0.0" + } + } + } + }, + "metro": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro/-/metro-0.76.7.tgz", + "integrity": "sha512-67ZGwDeumEPnrHI+pEDSKH2cx+C81Gx8Mn5qOtmGUPm/Up9Y4I1H2dJZ5n17MWzejNo0XAvPh0QL0CrlJEODVQ==", + "requires": { + "@babel/code-frame": "^7.0.0", + "@babel/core": "^7.20.0", + "@babel/generator": "^7.20.0", + "@babel/parser": "^7.20.0", + "@babel/template": "^7.0.0", + "@babel/traverse": "^7.20.0", + "@babel/types": "^7.20.0", + "accepts": "^1.3.7", + "async": "^3.2.2", + "chalk": "^4.0.0", + "ci-info": "^2.0.0", + "connect": "^3.6.5", + "debug": "^2.2.0", + "denodeify": "^1.2.1", + "error-stack-parser": "^2.0.6", + "graceful-fs": "^4.2.4", + "hermes-parser": "0.12.0", + "image-size": "^1.0.2", + "invariant": "^2.2.4", + "jest-worker": "^27.2.0", + "jsc-safe-url": "^0.2.2", + "lodash.throttle": "^4.1.1", + "metro-babel-transformer": "0.76.7", + "metro-cache": "0.76.7", + "metro-cache-key": "0.76.7", + "metro-config": "0.76.7", + "metro-core": "0.76.7", + "metro-file-map": "0.76.7", + "metro-inspector-proxy": "0.76.7", + "metro-minify-terser": "0.76.7", + "metro-minify-uglify": "0.76.7", + "metro-react-native-babel-preset": "0.76.7", + "metro-resolver": "0.76.7", + "metro-runtime": "0.76.7", + "metro-source-map": "0.76.7", + "metro-symbolicate": "0.76.7", + "metro-transform-plugins": "0.76.7", + "metro-transform-worker": "0.76.7", + "mime-types": "^2.1.27", + "node-fetch": "^2.2.0", + "nullthrows": "^1.1.1", + "rimraf": "^3.0.2", + "serialize-error": "^2.1.0", + "source-map": "^0.5.6", + "strip-ansi": "^6.0.0", + "throat": "^5.0.0", + "ws": "^7.5.1", + "yargs": "^17.6.2" + } + }, + "metro-babel-transformer": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-babel-transformer/-/metro-babel-transformer-0.76.7.tgz", + "integrity": "sha512-bgr2OFn0J4r0qoZcHrwEvccF7g9k3wdgTOgk6gmGHrtlZ1Jn3oCpklW/DfZ9PzHfjY2mQammKTc19g/EFGyOJw==", + "requires": { + "@babel/core": "^7.20.0", + "hermes-parser": "0.12.0", + "nullthrows": "^1.1.1" + } + }, + "metro-cache": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-cache/-/metro-cache-0.76.7.tgz", + "integrity": "sha512-nWBMztrs5RuSxZRI7hgFgob5PhYDmxICh9FF8anm9/ito0u0vpPvRxt7sRu8fyeD2AHdXqE7kX32rWY0LiXgeg==", + "requires": { + "metro-core": "0.76.7", + "rimraf": "^3.0.2" + } + }, + "metro-cache-key": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-cache-key/-/metro-cache-key-0.76.7.tgz", + "integrity": "sha512-0pecoIzwsD/Whn/Qfa+SDMX2YyasV0ndbcgUFx7w1Ct2sLHClujdhQ4ik6mvQmsaOcnGkIyN0zcceMDjC2+BFQ==" + }, + "metro-config": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-config/-/metro-config-0.76.7.tgz", + "integrity": "sha512-CFDyNb9bqxZemiChC/gNdXZ7OQkIwmXzkrEXivcXGbgzlt/b2juCv555GWJHyZSlorwnwJfY3uzAFu4A9iRVfg==", + "requires": { + "connect": "^3.6.5", + "cosmiconfig": "^5.0.5", + "jest-validate": "^29.2.1", + "metro": "0.76.7", + "metro-cache": "0.76.7", + "metro-core": "0.76.7", + "metro-runtime": "0.76.7" + } + }, + "metro-core": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-core/-/metro-core-0.76.7.tgz", + "integrity": "sha512-0b8KfrwPmwCMW+1V7ZQPkTy2tsEKZjYG9Pu1PTsu463Z9fxX7WaR0fcHFshv+J1CnQSUTwIGGjbNvj1teKe+pw==", + "requires": { + "lodash.throttle": "^4.1.1", + "metro-resolver": "0.76.7" + } + }, + "metro-file-map": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-file-map/-/metro-file-map-0.76.7.tgz", + "integrity": "sha512-s+zEkTcJ4mOJTgEE2ht4jIo1DZfeWreQR3tpT3gDV/Y/0UQ8aJBTv62dE775z0GLsWZApiblAYZsj7ZE8P06nw==", + "requires": { + "anymatch": "^3.0.3", + "debug": "^2.2.0", + "fb-watchman": "^2.0.0", + "fsevents": "^2.3.2", + "graceful-fs": "^4.2.4", + "invariant": "^2.2.4", + "jest-regex-util": "^27.0.6", + "jest-util": "^27.2.0", + "jest-worker": "^27.2.0", + "micromatch": "^4.0.4", + "node-abort-controller": "^3.1.1", + "nullthrows": "^1.1.1", + "walker": "^1.0.7" + } + }, + "metro-inspector-proxy": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-inspector-proxy/-/metro-inspector-proxy-0.76.7.tgz", + "integrity": "sha512-rNZ/6edTl/1qUekAhAbaFjczMphM50/UjtxiKulo6vqvgn/Mjd9hVqDvVYfAMZXqPvlusD88n38UjVYPkruLSg==", + "requires": { + "connect": "^3.6.5", + "debug": "^2.2.0", + "node-fetch": "^2.2.0", + "ws": "^7.5.1", + "yargs": "^17.6.2" + } + }, + "metro-minify-terser": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-minify-terser/-/metro-minify-terser-0.76.7.tgz", + "integrity": "sha512-FQiZGhIxCzhDwK4LxyPMLlq0Tsmla10X7BfNGlYFK0A5IsaVKNJbETyTzhpIwc+YFRT4GkFFwgo0V2N5vxO5HA==", + "requires": { + "terser": "^5.15.0" + } + }, + "metro-minify-uglify": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-minify-uglify/-/metro-minify-uglify-0.76.7.tgz", + "integrity": "sha512-FuXIU3j2uNcSvQtPrAJjYWHruPiQ+EpE++J9Z+VznQKEHcIxMMoQZAfIF2IpZSrZYfLOjVFyGMvj41jQMxV1Vw==", + "requires": { + "uglify-es": "^3.1.9" + } + }, + "metro-react-native-babel-preset": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-react-native-babel-preset/-/metro-react-native-babel-preset-0.76.7.tgz", + "integrity": "sha512-R25wq+VOSorAK3hc07NW0SmN8z9S/IR0Us0oGAsBcMZnsgkbOxu77Mduqf+f4is/wnWHc5+9bfiqdLnaMngiVw==", + "requires": { + "@babel/core": "^7.20.0", + "@babel/plugin-proposal-async-generator-functions": "^7.0.0", + "@babel/plugin-proposal-class-properties": "^7.18.0", + "@babel/plugin-proposal-export-default-from": "^7.0.0", + "@babel/plugin-proposal-nullish-coalescing-operator": "^7.18.0", + "@babel/plugin-proposal-numeric-separator": "^7.0.0", + "@babel/plugin-proposal-object-rest-spread": "^7.20.0", + "@babel/plugin-proposal-optional-catch-binding": "^7.0.0", + "@babel/plugin-proposal-optional-chaining": "^7.20.0", + "@babel/plugin-syntax-dynamic-import": "^7.8.0", + "@babel/plugin-syntax-export-default-from": "^7.0.0", + "@babel/plugin-syntax-flow": "^7.18.0", + "@babel/plugin-syntax-nullish-coalescing-operator": "^7.0.0", + "@babel/plugin-syntax-optional-chaining": "^7.0.0", + "@babel/plugin-transform-arrow-functions": "^7.0.0", + "@babel/plugin-transform-async-to-generator": "^7.20.0", + "@babel/plugin-transform-block-scoping": "^7.0.0", + "@babel/plugin-transform-classes": "^7.0.0", + "@babel/plugin-transform-computed-properties": "^7.0.0", + "@babel/plugin-transform-destructuring": "^7.20.0", + "@babel/plugin-transform-flow-strip-types": "^7.20.0", + "@babel/plugin-transform-function-name": "^7.0.0", + "@babel/plugin-transform-literals": "^7.0.0", + "@babel/plugin-transform-modules-commonjs": "^7.0.0", + "@babel/plugin-transform-named-capturing-groups-regex": "^7.0.0", + "@babel/plugin-transform-parameters": "^7.0.0", + "@babel/plugin-transform-react-display-name": "^7.0.0", + "@babel/plugin-transform-react-jsx": "^7.0.0", + "@babel/plugin-transform-react-jsx-self": "^7.0.0", + "@babel/plugin-transform-react-jsx-source": "^7.0.0", + "@babel/plugin-transform-runtime": "^7.0.0", + "@babel/plugin-transform-shorthand-properties": "^7.0.0", + "@babel/plugin-transform-spread": "^7.0.0", + "@babel/plugin-transform-sticky-regex": "^7.0.0", + "@babel/plugin-transform-typescript": "^7.5.0", + "@babel/plugin-transform-unicode-regex": "^7.0.0", + "@babel/template": "^7.0.0", + "babel-plugin-transform-flow-enums": "^0.0.2", + "react-refresh": "^0.4.0" + } + }, + "metro-react-native-babel-transformer": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-react-native-babel-transformer/-/metro-react-native-babel-transformer-0.76.7.tgz", + "integrity": "sha512-W6lW3J7y/05ph3c2p3KKJNhH0IdyxdOCbQ5it7aM2MAl0SM4wgKjaV6EYv9b3rHklpV6K3qMH37UKVcjMooWiA==", + "requires": { + "@babel/core": "^7.20.0", + "babel-preset-fbjs": "^3.4.0", + "hermes-parser": "0.12.0", + "metro-react-native-babel-preset": "0.76.7", + "nullthrows": "^1.1.1" + } + }, + "metro-resolver": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-resolver/-/metro-resolver-0.76.7.tgz", + "integrity": "sha512-pC0Wgq29HHIHrwz23xxiNgylhI8Rq1V01kQaJ9Kz11zWrIdlrH0ZdnJ7GC6qA0ErROG+cXmJ0rJb8/SW1Zp2IA==" + }, + "metro-runtime": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-runtime/-/metro-runtime-0.76.7.tgz", + "integrity": "sha512-MuWHubQHymUWBpZLwuKZQgA/qbb35WnDAKPo83rk7JRLIFPvzXSvFaC18voPuzJBt1V98lKQIonh6MiC9gd8Ug==", + "requires": { + "@babel/runtime": "^7.0.0", + "react-refresh": "^0.4.0" + } + }, + "metro-source-map": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-source-map/-/metro-source-map-0.76.7.tgz", + "integrity": "sha512-Prhx7PeRV1LuogT0Kn5VjCuFu9fVD68eefntdWabrksmNY6mXK8pRqzvNJOhTojh6nek+RxBzZeD6MIOOyXS6w==", + "requires": { + "@babel/traverse": "^7.20.0", + "@babel/types": "^7.20.0", + "invariant": "^2.2.4", + "metro-symbolicate": "0.76.7", + "nullthrows": "^1.1.1", + "ob1": "0.76.7", + "source-map": "^0.5.6", + "vlq": "^1.0.0" + } + }, + "metro-symbolicate": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-symbolicate/-/metro-symbolicate-0.76.7.tgz", + "integrity": "sha512-p0zWEME5qLSL1bJb93iq+zt5fz3sfVn9xFYzca1TJIpY5MommEaS64Va87lp56O0sfEIvh4307Oaf/ZzRjuLiQ==", + "requires": { + "invariant": "^2.2.4", + "metro-source-map": "0.76.7", + "nullthrows": "^1.1.1", + "source-map": "^0.5.6", + "through2": "^2.0.1", + "vlq": "^1.0.0" + } + }, + "metro-transform-plugins": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-transform-plugins/-/metro-transform-plugins-0.76.7.tgz", + "integrity": "sha512-iSmnjVApbdivjuzb88Orb0JHvcEt5veVyFAzxiS5h0QB+zV79w6JCSqZlHCrbNOkOKBED//LqtKbFVakxllnNg==", + "requires": { + "@babel/core": "^7.20.0", + "@babel/generator": "^7.20.0", + "@babel/template": "^7.0.0", + "@babel/traverse": "^7.20.0", + "nullthrows": "^1.1.1" + } + }, + "metro-transform-worker": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/metro-transform-worker/-/metro-transform-worker-0.76.7.tgz", + "integrity": "sha512-cGvELqFMVk9XTC15CMVzrCzcO6sO1lURfcbgjuuPdzaWuD11eEyocvkTX0DPiRjsvgAmicz4XYxVzgYl3MykDw==", + "requires": { + "@babel/core": "^7.20.0", + "@babel/generator": "^7.20.0", + "@babel/parser": "^7.20.0", + "@babel/types": "^7.20.0", + "babel-preset-fbjs": "^3.4.0", + "metro": "0.76.7", + "metro-babel-transformer": "0.76.7", + "metro-cache": "0.76.7", + "metro-cache-key": "0.76.7", + "metro-source-map": "0.76.7", + "metro-transform-plugins": "0.76.7", + "nullthrows": "^1.1.1" + } + }, + "ms": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" + }, + "ob1": { + "version": "0.76.7", + "resolved": "https://registry.npmjs.org/ob1/-/ob1-0.76.7.tgz", + "integrity": "sha512-BQdRtxxoUNfSoZxqeBGOyuT9nEYSn18xZHwGMb0mMVpn2NBcYbnyKY4BK2LIHRgw33CBGlUmE+KMaNvyTpLLtQ==" + }, + "parse-json": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", + "integrity": "sha512-aOIos8bujGN93/8Ox/jPLh7RwVnPEysynVFE+fQZyg6jKELEHwzgKdLRFHUgXJL6kylijVSBC4BvN9OmsB48Rw==", + "requires": { + "error-ex": "^1.3.1", + "json-parse-better-errors": "^1.0.1" + } + }, + "react-refresh": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/react-refresh/-/react-refresh-0.4.3.tgz", + "integrity": "sha512-Hwln1VNuGl/6bVwnd0Xdn1e84gT/8T9aYNL+HAKDArLCS7LWjwr7StE30IEYbIkx0Vi3vs+coQxe+SQDbGbbpA==" + }, + "resolve-from": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-3.0.0.tgz", + "integrity": "sha512-GnlH6vxLymXJNMBo7XP1fJIzBFbdYt49CuTwmB/6N53t+kMPRMFKz783LlQ4tv28XoQfMWinAJX6WCGf2IlaIw==" + }, + "serialize-error": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/serialize-error/-/serialize-error-2.1.0.tgz", + "integrity": "sha512-ghgmKt5o4Tly5yEG/UJp8qTd0AN7Xalw4XBtDEKP655B699qMEtra1WlXeE6WIvdEG481JvRxULKsInq/iNysw==" + }, + "source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha512-LbrmJOMUSdEVxIKvdcJzQC+nQhe8FUZQTXQy6+I75skNgn3OoQ0DZA8YnFa7gp8tqtL3KPf1kmo0R5DoApeSGQ==" + }, "supports-color": { "version": "7.2.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", @@ -53124,16 +54196,46 @@ "requires": { "has-flag": "^4.0.0" } + }, + "ws": { + "version": "7.5.9", + "resolved": "https://registry.npmjs.org/ws/-/ws-7.5.9.tgz", + "integrity": "sha512-F+P9Jil7UiSKSkppIiD94dN07AwvFixvLIj1Og1Rl9GGMuNipJnV9JzjD6XuqmAeiswGvUmNLjr5cFuXwNS77Q==", + "requires": {} + }, + "y18n": { + "version": "5.0.8", + "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", + "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==" + }, + "yargs": { + "version": "17.7.2", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", + "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", + "requires": { + "cliui": "^8.0.1", + "escalade": "^3.1.1", + "get-caller-file": "^2.0.5", + "require-directory": "^2.1.1", + "string-width": "^4.2.3", + "y18n": "^5.0.5", + "yargs-parser": "^21.1.1" + } + }, + "yargs-parser": { + "version": "21.1.1", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz", + "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==" } } }, "@react-native-community/cli-server-api": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-server-api/-/cli-server-api-11.3.5.tgz", - "integrity": "sha512-PM/jF13uD1eAKuC84lntNuM5ZvJAtyb+H896P1dBIXa9boPLa3KejfUvNVoyOUJ5s8Ht25JKbc3yieV2+GMBDA==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-server-api/-/cli-server-api-11.3.6.tgz", + "integrity": "sha512-8GUKodPnURGtJ9JKg8yOHIRtWepPciI3ssXVw5jik7+dZ43yN8P5BqCoDaq8e1H1yRer27iiOfT7XVnwk8Dueg==", "requires": { - "@react-native-community/cli-debugger-ui": "11.3.5", - "@react-native-community/cli-tools": "11.3.5", + "@react-native-community/cli-debugger-ui": "11.3.6", + "@react-native-community/cli-tools": "11.3.6", "compression": "^1.7.1", "connect": "^3.6.5", "errorhandler": "^1.5.1", @@ -53194,9 +54296,9 @@ } }, "@react-native-community/cli-tools": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-tools/-/cli-tools-11.3.5.tgz", - "integrity": "sha512-zDklE1+ah/zL4BLxut5XbzqCj9KTHzbYBKX7//cXw2/0TpkNCaY9c+iKx//gZ5m7U1OKbb86Fm2b0AKtKVRf6Q==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-tools/-/cli-tools-11.3.6.tgz", + "integrity": "sha512-JpmUTcDwAGiTzLsfMlIAYpCMSJ9w2Qlf7PU7mZIRyEu61UzEawyw83DkqfbzDPBuRwRnaeN44JX2CP/yTO3ThQ==", "requires": { "appdirsjs": "^1.2.4", "chalk": "^4.1.2", @@ -53205,7 +54307,7 @@ "node-fetch": "^2.6.0", "open": "^6.2.0", "ora": "^5.4.1", - "semver": "^6.3.0", + "semver": "^7.5.2", "shell-quote": "^1.7.3" }, "dependencies": { @@ -53257,11 +54359,6 @@ "is-wsl": "^1.1.0" } }, - "semver": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz", - "integrity": "sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==" - }, "supports-color": { "version": "7.2.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", @@ -53273,9 +54370,9 @@ } }, "@react-native-community/cli-types": { - "version": "11.3.5", - "resolved": "https://registry.npmjs.org/@react-native-community/cli-types/-/cli-types-11.3.5.tgz", - "integrity": "sha512-pf0kdWMEfPSV/+8rcViDCFzbLMtWIHMZ8ay7hKwqaoWegsJ0oprSF2tSTH+LSC/7X1Beb9ssIvHj1m5C4es5Xg==", + "version": "11.3.6", + "resolved": "https://registry.npmjs.org/@react-native-community/cli-types/-/cli-types-11.3.6.tgz", + "integrity": "sha512-6DxjrMKx5x68N/tCJYVYRKAtlRHbtUVBZrnAvkxbRWFD9v4vhNgsPM0RQm8i2vRugeksnao5mbnRGpS6c0awCw==", "requires": { "joi": "^17.2.1" } @@ -53419,15 +54516,15 @@ "version": "0.72.1" }, "@react-native/metro-config": { - "version": "0.72.9", - "resolved": "https://registry.npmjs.org/@react-native/metro-config/-/metro-config-0.72.9.tgz", - "integrity": "sha512-5MGmyDnXPeprRuvgPGE4LZ+e+ovofSd5YY6nFDwg6wbjRGOkeCRRlaTlQT+fjmv+zr4vYG+MUTKBlaO+fui/vA==", + "version": "0.72.11", + "resolved": "https://registry.npmjs.org/@react-native/metro-config/-/metro-config-0.72.11.tgz", + "integrity": "sha512-661EyQnDdVelyc0qP/ew7kKkGAh6N6KlkuPLC2SQ8sxaXskVU6fSuNlpLW4bUTBUDFKG8gEOU2hp6rzk4wQnGQ==", "dev": true, "requires": { "@react-native/js-polyfills": "^0.72.1", - "metro-config": "0.76.7", - "metro-react-native-babel-transformer": "0.76.7", - "metro-runtime": "0.76.7" + "metro-config": "0.76.8", + "metro-react-native-babel-transformer": "0.76.8", + "metro-runtime": "0.76.8" } }, "@react-native/normalize-color": { @@ -53439,9 +54536,9 @@ "integrity": "sha512-285lfdqSXaqKuBbbtP9qL2tDrfxdOFtIMvkKadtleRQkdOxx+uzGvFr82KHmc/sSiMtfXGp7JnFYWVh4sFl7Yw==" }, "@react-native/virtualized-lists": { - "version": "0.72.6", - "resolved": "https://registry.npmjs.org/@react-native/virtualized-lists/-/virtualized-lists-0.72.6.tgz", - "integrity": "sha512-JhT6ydu35LvbSKdwnhWDuGHMOwM0WAh9oza/X8vXHA8ELHRyQ/4p8eKz/bTQcbQziJaaleUURToGhFuCtgiMoA==", + "version": "0.72.8", + "resolved": "https://registry.npmjs.org/@react-native/virtualized-lists/-/virtualized-lists-0.72.8.tgz", + "integrity": "sha512-J3Q4Bkuo99k7mu+jPS9gSUSgq+lLRSI/+ahXNwV92XgJ/8UgOTxu2LPwhJnBk/sQKxq7E8WkZBnBiozukQMqrw==", "requires": { "invariant": "^2.2.4", "nullthrows": "^1.1.1" @@ -62651,7 +63748,9 @@ "dev": true }, "babel-plugin-syntax-trailing-function-commas": { - "version": "7.0.0-beta.0" + "version": "7.0.0-beta.0", + "resolved": "https://registry.npmjs.org/babel-plugin-syntax-trailing-function-commas/-/babel-plugin-syntax-trailing-function-commas-7.0.0-beta.0.tgz", + "integrity": "sha512-Xj9XuRuz3nTSbaTXWv3itLOcxyF4oPD8douBBmj7U9BBC6nEBYfyOJYQMf/8PJAFotC62UY5dFfIGEPr7WswzQ==" }, "babel-plugin-transform-class-properties": { "version": "6.24.1", @@ -62708,6 +63807,8 @@ }, "babel-preset-fbjs": { "version": "3.4.0", + "resolved": "https://registry.npmjs.org/babel-preset-fbjs/-/babel-preset-fbjs-3.4.0.tgz", + "integrity": "sha512-9ywCsCvo1ojrw0b+XYk7aFvTH6D9064t0RIL1rtMf3nsa02Xw41MS7sZw216Im35xj/UY0PDBQsa1brUDDF1Ow==", "requires": { "@babel/plugin-proposal-class-properties": "^7.0.0", "@babel/plugin-proposal-object-rest-spread": "^7.0.0", @@ -63787,9 +64888,9 @@ } }, "cli-spinners": { - "version": "2.9.0", - "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-2.9.0.tgz", - "integrity": "sha512-4/aL9X3Wh0yiMQlE+eeRhWP6vclO3QRtw1JHKIT0FFUs5FjpFmESqtMvYZ0+lbzBw900b95mS0hohy+qn2VK/g==" + "version": "2.9.1", + "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-2.9.1.tgz", + "integrity": "sha512-jHgecW0pxkonBJdrKsqxgRX9AcG+u/5k0Q7WPDfi8AogLAdwxEkyYYNWwZ5GvVFoFx2uiY1eNcSK00fh+1+FyQ==" }, "cli-table3": { "version": "0.6.3", @@ -64108,6 +65209,8 @@ }, "connect": { "version": "3.7.0", + "resolved": "https://registry.npmjs.org/connect/-/connect-3.7.0.tgz", + "integrity": "sha512-ZqRXc+tZukToSNmh5C2iWMSoV3X1YUcPbqEM4DkEG5tNQXrQUZCNVGGv3IuicnkMtPfGf3Xtp8WCXs295iQ1pQ==", "requires": { "debug": "2.6.9", "finalhandler": "1.1.2", @@ -64117,12 +65220,16 @@ "dependencies": { "debug": { "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", "requires": { "ms": "2.0.0" } }, "finalhandler": { "version": "1.1.2", + "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.2.tgz", + "integrity": "sha512-aAWcW57uxVNrQZqFXjITpW3sIUQmHGG3qSb9mUah9MgMC4NeWhNOlNjXEYq3HjRAvL6arUviZGGJsBg6z0zsWA==", "requires": { "debug": "2.6.9", "encodeurl": "~1.0.2", @@ -64134,16 +65241,22 @@ } }, "ms": { - "version": "2.0.0" + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" }, "on-finished": { "version": "2.3.0", + "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.3.0.tgz", + "integrity": "sha512-ikqdkGAAyf/X/gPhXGvfgAytDZtDbr+bkNUJ0N9h5MI/dmdgCs3l6hoHrcUv41sRKew3jIwrp4qQDXiK99Utww==", "requires": { "ee-first": "1.1.1" } }, "statuses": { - "version": "1.5.0" + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", + "integrity": "sha512-OpZ3zP+jT1PI7I8nemJX4AKmAX070ZkYPVWV/AaKTJl+tXCTGyVdC1a4SL8RUQYEwk/f34ZX8UTykN68FwrqAA==" } } }, @@ -65075,7 +66188,9 @@ "dev": true }, "denodeify": { - "version": "1.2.1" + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/denodeify/-/denodeify-1.2.1.tgz", + "integrity": "sha512-KNTihKNmQENUZeKu5fzfpzRqR5S2VMp4gl9RFHiWzj9DfvYQPMJ6XHKNaQxaGCXwPk6y9yme3aUoaiAe+KX+vg==" }, "depd": { "version": "2.0.0" @@ -66154,9 +67269,9 @@ } }, "eslint-config-expensify": { - "version": "2.0.38", - "resolved": "https://registry.npmjs.org/eslint-config-expensify/-/eslint-config-expensify-2.0.38.tgz", - "integrity": "sha512-jAlrYSjkDV8YESUUPcaTjUM8Fgru+37FS+Hq6zzcRR0FbA5bLiOPguhJHo77XpYh5N+PEf4wrpgsS04sjdgDPg==", + "version": "2.0.39", + "resolved": "https://registry.npmjs.org/eslint-config-expensify/-/eslint-config-expensify-2.0.39.tgz", + "integrity": "sha512-DIxR3k99ZIDPE2NK+WLLRWpoDq06gTXdY8XZg9Etd1UqZ7fXm/Yz3/QkTxu7CH7UaXbCH3P4PTo023ULQGKOSw==", "dev": true, "requires": { "@lwc/eslint-plugin-lwc": "^0.11.0", @@ -67143,9 +68258,9 @@ } }, "expensify-common": { - "version": "git+ssh://git@github.com/Expensify/expensify-common.git#35bff866a8d345b460ea6256f0a0f0a8a7f81086", - "integrity": "sha512-O0KbaMljSFyoZXcxtx5B2qBL+n0md3wYOrArMVT8N0W+4wKncn+p8/vrmVlUMHe/vDloUbVmUZNdHwOZNWdx3w==", - "from": "expensify-common@git+ssh://git@github.com/Expensify/expensify-common.git#35bff866a8d345b460ea6256f0a0f0a8a7f81086", + "version": "git+ssh://git@github.com/Expensify/expensify-common.git#1609f1848cc0c2528064519c3ea48b4953a708ee", + "integrity": "sha512-sUd/ky6xCB/mShVaD2nVkedGL2xy+h6Jf5MfX9GOiYX8wB2D8uZSpqswz515uwcp8RDWrA5wxM2cR6pBXNfgxw==", + "from": "expensify-common@git+ssh://git@github.com/Expensify/expensify-common.git#1609f1848cc0c2528064519c3ea48b4953a708ee", "requires": { "classnames": "2.3.1", "clipboard": "2.0.4", @@ -71175,9 +72290,9 @@ } }, "joi": { - "version": "17.9.2", - "resolved": "https://registry.npmjs.org/joi/-/joi-17.9.2.tgz", - "integrity": "sha512-Itk/r+V4Dx0V3c7RLFdRh12IOjySm2/WGPMubBT92cQvRfYZhPM2W0hZlctjj72iES8jsRCwp7S/cRmWBnJ4nw==", + "version": "17.10.1", + "resolved": "https://registry.npmjs.org/joi/-/joi-17.10.1.tgz", + "integrity": "sha512-vIiDxQKmRidUVp8KngT8MZSOcmRVm2zV7jbMjNYWuHcJWI0bUck3nRTGQjhpPlQenIQIBC5Vp9AhcnHbWQqafw==", "requires": { "@hapi/hoek": "^9.0.0", "@hapi/topo": "^5.0.0", @@ -71635,7 +72750,9 @@ "dev": true }, "lodash.throttle": { - "version": "4.1.1" + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/lodash.throttle/-/lodash.throttle-4.1.1.tgz", + "integrity": "sha512-wIkUCfVKpVsWo3JSZlc+8MB5it+2AN5W8J7YVMST30UrvcQNZ1Okbj+rbVniijTWE6FGYy4XJq/rHkas8qJMLQ==" }, "lodash.truncate": { "version": "4.4.2", @@ -72639,9 +73756,10 @@ "dev": true }, "metro": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro/-/metro-0.76.7.tgz", - "integrity": "sha512-67ZGwDeumEPnrHI+pEDSKH2cx+C81Gx8Mn5qOtmGUPm/Up9Y4I1H2dJZ5n17MWzejNo0XAvPh0QL0CrlJEODVQ==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro/-/metro-0.76.8.tgz", + "integrity": "sha512-oQA3gLzrrYv3qKtuWArMgHPbHu8odZOD9AoavrqSFllkPgOtmkBvNNDLCELqv5SjBfqjISNffypg+5UGG3y0pg==", + "dev": true, "requires": { "@babel/code-frame": "^7.0.0", "@babel/core": "^7.20.0", @@ -72665,22 +73783,22 @@ "jest-worker": "^27.2.0", "jsc-safe-url": "^0.2.2", "lodash.throttle": "^4.1.1", - "metro-babel-transformer": "0.76.7", - "metro-cache": "0.76.7", - "metro-cache-key": "0.76.7", - "metro-config": "0.76.7", - "metro-core": "0.76.7", - "metro-file-map": "0.76.7", - "metro-inspector-proxy": "0.76.7", - "metro-minify-terser": "0.76.7", - "metro-minify-uglify": "0.76.7", - "metro-react-native-babel-preset": "0.76.7", - "metro-resolver": "0.76.7", - "metro-runtime": "0.76.7", - "metro-source-map": "0.76.7", - "metro-symbolicate": "0.76.7", - "metro-transform-plugins": "0.76.7", - "metro-transform-worker": "0.76.7", + "metro-babel-transformer": "0.76.8", + "metro-cache": "0.76.8", + "metro-cache-key": "0.76.8", + "metro-config": "0.76.8", + "metro-core": "0.76.8", + "metro-file-map": "0.76.8", + "metro-inspector-proxy": "0.76.8", + "metro-minify-terser": "0.76.8", + "metro-minify-uglify": "0.76.8", + "metro-react-native-babel-preset": "0.76.8", + "metro-resolver": "0.76.8", + "metro-runtime": "0.76.8", + "metro-source-map": "0.76.8", + "metro-symbolicate": "0.76.8", + "metro-transform-plugins": "0.76.8", + "metro-transform-worker": "0.76.8", "mime-types": "^2.1.27", "node-fetch": "^2.2.0", "nullthrows": "^1.1.1", @@ -72697,6 +73815,7 @@ "version": "4.3.0", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, "requires": { "color-convert": "^2.0.1" } @@ -72705,6 +73824,7 @@ "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, "requires": { "ansi-styles": "^4.1.0", "supports-color": "^7.1.0" @@ -72713,12 +73833,14 @@ "ci-info": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-2.0.0.tgz", - "integrity": "sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==" + "integrity": "sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==", + "dev": true }, "cliui": { "version": "8.0.1", "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", "integrity": "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==", + "dev": true, "requires": { "string-width": "^4.2.0", "strip-ansi": "^6.0.1", @@ -72729,6 +73851,7 @@ "version": "2.0.1", "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, "requires": { "color-name": "~1.1.4" } @@ -72736,12 +73859,14 @@ "color-name": { "version": "1.1.4", "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true }, "debug": { "version": "2.6.9", "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, "requires": { "ms": "2.0.0" } @@ -72749,12 +73874,14 @@ "has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==" + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true }, "jest-worker": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", + "dev": true, "requires": { "@types/node": "*", "merge-stream": "^2.0.0", @@ -72765,6 +73892,7 @@ "version": "8.1.1", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "dev": true, "requires": { "has-flag": "^4.0.0" } @@ -72774,22 +73902,26 @@ "ms": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true }, "serialize-error": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/serialize-error/-/serialize-error-2.1.0.tgz", - "integrity": "sha512-ghgmKt5o4Tly5yEG/UJp8qTd0AN7Xalw4XBtDEKP655B699qMEtra1WlXeE6WIvdEG481JvRxULKsInq/iNysw==" + "integrity": "sha512-ghgmKt5o4Tly5yEG/UJp8qTd0AN7Xalw4XBtDEKP655B699qMEtra1WlXeE6WIvdEG481JvRxULKsInq/iNysw==", + "dev": true }, "source-map": { "version": "0.5.7", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha512-LbrmJOMUSdEVxIKvdcJzQC+nQhe8FUZQTXQy6+I75skNgn3OoQ0DZA8YnFa7gp8tqtL3KPf1kmo0R5DoApeSGQ==" + "integrity": "sha512-LbrmJOMUSdEVxIKvdcJzQC+nQhe8FUZQTXQy6+I75skNgn3OoQ0DZA8YnFa7gp8tqtL3KPf1kmo0R5DoApeSGQ==", + "dev": true }, "supports-color": { "version": "7.2.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, "requires": { "has-flag": "^4.0.0" } @@ -72798,17 +73930,20 @@ "version": "7.5.9", "resolved": "https://registry.npmjs.org/ws/-/ws-7.5.9.tgz", "integrity": "sha512-F+P9Jil7UiSKSkppIiD94dN07AwvFixvLIj1Og1Rl9GGMuNipJnV9JzjD6XuqmAeiswGvUmNLjr5cFuXwNS77Q==", + "dev": true, "requires": {} }, "y18n": { "version": "5.0.8", "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", - "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==" + "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==", + "dev": true }, "yargs": { "version": "17.7.2", "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", + "dev": true, "requires": { "cliui": "^8.0.1", "escalade": "^3.1.1", @@ -72822,14 +73957,16 @@ "yargs-parser": { "version": "21.1.1", "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz", - "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==" + "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==", + "dev": true } } }, "metro-babel-transformer": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-babel-transformer/-/metro-babel-transformer-0.76.7.tgz", - "integrity": "sha512-bgr2OFn0J4r0qoZcHrwEvccF7g9k3wdgTOgk6gmGHrtlZ1Jn3oCpklW/DfZ9PzHfjY2mQammKTc19g/EFGyOJw==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-babel-transformer/-/metro-babel-transformer-0.76.8.tgz", + "integrity": "sha512-Hh6PW34Ug/nShlBGxkwQJSgPGAzSJ9FwQXhUImkzdsDgVu6zj5bx258J8cJVSandjNoQ8nbaHK6CaHlnbZKbyA==", + "dev": true, "requires": { "@babel/core": "^7.20.0", "hermes-parser": "0.12.0", @@ -72837,37 +73974,41 @@ } }, "metro-cache": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-cache/-/metro-cache-0.76.7.tgz", - "integrity": "sha512-nWBMztrs5RuSxZRI7hgFgob5PhYDmxICh9FF8anm9/ito0u0vpPvRxt7sRu8fyeD2AHdXqE7kX32rWY0LiXgeg==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-cache/-/metro-cache-0.76.8.tgz", + "integrity": "sha512-QBJSJIVNH7Hc/Yo6br/U/qQDUpiUdRgZ2ZBJmvAbmAKp2XDzsapnMwK/3BGj8JNWJF7OLrqrYHsRsukSbUBpvQ==", + "dev": true, "requires": { - "metro-core": "0.76.7", + "metro-core": "0.76.8", "rimraf": "^3.0.2" } }, "metro-cache-key": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-cache-key/-/metro-cache-key-0.76.7.tgz", - "integrity": "sha512-0pecoIzwsD/Whn/Qfa+SDMX2YyasV0ndbcgUFx7w1Ct2sLHClujdhQ4ik6mvQmsaOcnGkIyN0zcceMDjC2+BFQ==" + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-cache-key/-/metro-cache-key-0.76.8.tgz", + "integrity": "sha512-buKQ5xentPig9G6T37Ww/R/bC+/V1MA5xU/D8zjnhlelsrPG6w6LtHUS61ID3zZcMZqYaELWk5UIadIdDsaaLw==", + "dev": true }, "metro-config": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-config/-/metro-config-0.76.7.tgz", - "integrity": "sha512-CFDyNb9bqxZemiChC/gNdXZ7OQkIwmXzkrEXivcXGbgzlt/b2juCv555GWJHyZSlorwnwJfY3uzAFu4A9iRVfg==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-config/-/metro-config-0.76.8.tgz", + "integrity": "sha512-SL1lfKB0qGHALcAk2zBqVgQZpazDYvYFGwCK1ikz0S6Y/CM2i2/HwuZN31kpX6z3mqjv/6KvlzaKoTb1otuSAA==", + "dev": true, "requires": { "connect": "^3.6.5", "cosmiconfig": "^5.0.5", "jest-validate": "^29.2.1", - "metro": "0.76.7", - "metro-cache": "0.76.7", - "metro-core": "0.76.7", - "metro-runtime": "0.76.7" + "metro": "0.76.8", + "metro-cache": "0.76.8", + "metro-core": "0.76.8", + "metro-runtime": "0.76.8" }, "dependencies": { "cosmiconfig": { "version": "5.2.1", "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-5.2.1.tgz", "integrity": "sha512-H65gsXo1SKjf8zmrJ67eJk8aIRKV5ff2D4uKZIBZShbhGSpEmsQOPW/SKMKYhSTrqR7ufy6RP69rPogdaPh/kA==", + "dev": true, "requires": { "import-fresh": "^2.0.0", "is-directory": "^0.3.1", @@ -72879,6 +74020,7 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-2.0.0.tgz", "integrity": "sha512-eZ5H8rcgYazHbKC3PG4ClHNykCSxtAhxSSEM+2mb+7evD2CKF5V7c0dNum7AdpDh0ZdICwZY9sRSn8f+KH96sg==", + "dev": true, "requires": { "caller-path": "^2.0.0", "resolve-from": "^3.0.0" @@ -72888,6 +74030,7 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", "integrity": "sha512-aOIos8bujGN93/8Ox/jPLh7RwVnPEysynVFE+fQZyg6jKELEHwzgKdLRFHUgXJL6kylijVSBC4BvN9OmsB48Rw==", + "dev": true, "requires": { "error-ex": "^1.3.1", "json-parse-better-errors": "^1.0.1" @@ -72896,23 +74039,26 @@ "resolve-from": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-3.0.0.tgz", - "integrity": "sha512-GnlH6vxLymXJNMBo7XP1fJIzBFbdYt49CuTwmB/6N53t+kMPRMFKz783LlQ4tv28XoQfMWinAJX6WCGf2IlaIw==" + "integrity": "sha512-GnlH6vxLymXJNMBo7XP1fJIzBFbdYt49CuTwmB/6N53t+kMPRMFKz783LlQ4tv28XoQfMWinAJX6WCGf2IlaIw==", + "dev": true } } }, "metro-core": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-core/-/metro-core-0.76.7.tgz", - "integrity": "sha512-0b8KfrwPmwCMW+1V7ZQPkTy2tsEKZjYG9Pu1PTsu463Z9fxX7WaR0fcHFshv+J1CnQSUTwIGGjbNvj1teKe+pw==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-core/-/metro-core-0.76.8.tgz", + "integrity": "sha512-sl2QLFI3d1b1XUUGxwzw/KbaXXU/bvFYrSKz6Sg19AdYGWFyzsgZ1VISRIDf+HWm4R/TJXluhWMEkEtZuqi3qA==", + "dev": true, "requires": { "lodash.throttle": "^4.1.1", - "metro-resolver": "0.76.7" + "metro-resolver": "0.76.8" } }, "metro-file-map": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-file-map/-/metro-file-map-0.76.7.tgz", - "integrity": "sha512-s+zEkTcJ4mOJTgEE2ht4jIo1DZfeWreQR3tpT3gDV/Y/0UQ8aJBTv62dE775z0GLsWZApiblAYZsj7ZE8P06nw==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-file-map/-/metro-file-map-0.76.8.tgz", + "integrity": "sha512-A/xP1YNEVwO1SUV9/YYo6/Y1MmzhL4ZnVgcJC3VmHp/BYVOXVStzgVbWv2wILe56IIMkfXU+jpXrGKKYhFyHVw==", + "dev": true, "requires": { "anymatch": "^3.0.3", "debug": "^2.2.0", @@ -72933,6 +74079,7 @@ "version": "27.5.1", "resolved": "https://registry.npmjs.org/@jest/types/-/types-27.5.1.tgz", "integrity": "sha512-Cx46iJ9QpwQTjIdq5VJu2QTMMs3QlEjI0x1QbBP5W1+nMzyc2XmimiRR/CbX9TO0cPTeUlxWMOu8mslYsJ8DEw==", + "dev": true, "requires": { "@types/istanbul-lib-coverage": "^2.0.0", "@types/istanbul-reports": "^3.0.0", @@ -72945,6 +74092,7 @@ "version": "16.0.5", "resolved": "https://registry.npmjs.org/@types/yargs/-/yargs-16.0.5.tgz", "integrity": "sha512-AxO/ADJOBFJScHbWhq2xAhlWP24rY4aCEG/NFaMvbT3X2MgRsLjhjQwsn0Zi5zn0LG9jUhCCZMeX9Dkuw6k+vQ==", + "dev": true, "requires": { "@types/yargs-parser": "*" } @@ -72953,6 +74101,7 @@ "version": "4.3.0", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, "requires": { "color-convert": "^2.0.1" } @@ -72961,6 +74110,7 @@ "version": "4.1.2", "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, "requires": { "ansi-styles": "^4.1.0", "supports-color": "^7.1.0" @@ -72970,6 +74120,7 @@ "version": "2.0.1", "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, "requires": { "color-name": "~1.1.4" } @@ -72977,12 +74128,14 @@ "color-name": { "version": "1.1.4", "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", - "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true }, "debug": { "version": "2.6.9", "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, "requires": { "ms": "2.0.0" } @@ -72990,17 +74143,20 @@ "has-flag": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", - "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==" + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true }, "jest-regex-util": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-regex-util/-/jest-regex-util-27.5.1.tgz", - "integrity": "sha512-4bfKq2zie+x16okqDXjXn9ql2B0dScQu+vcwe4TvFVhkVyuWLqpZrZtXxLLWoXYgn0E87I6r6GRYHF7wFZBUvg==" + "integrity": "sha512-4bfKq2zie+x16okqDXjXn9ql2B0dScQu+vcwe4TvFVhkVyuWLqpZrZtXxLLWoXYgn0E87I6r6GRYHF7wFZBUvg==", + "dev": true }, "jest-util": { "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-27.5.1.tgz", "integrity": "sha512-Kv2o/8jNvX1MQ0KGtw480E/w4fBCDOnH6+6DmeKi6LZUIlKA5kwY0YNdlzaWTiVgxqAqik11QyxDOKk543aKXw==", + "dev": true, "requires": { "@jest/types": "^27.5.1", "@types/node": "*", @@ -73014,6 +74170,7 @@ "version": "27.5.1", "resolved": "https://registry.npmjs.org/jest-worker/-/jest-worker-27.5.1.tgz", "integrity": "sha512-7vuh85V5cdDofPyxn58nrPjBktZo0u9x1g8WtjQol+jZDaE+fhN+cIvTj11GndBnMnyfrUOG1sZQxCdjKh+DKg==", + "dev": true, "requires": { "@types/node": "*", "merge-stream": "^2.0.0", @@ -73024,6 +74181,7 @@ "version": "8.1.1", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "dev": true, "requires": { "has-flag": "^4.0.0" } @@ -73033,12 +74191,14 @@ "ms": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true }, "supports-color": { "version": "7.2.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, "requires": { "has-flag": "^4.0.0" } @@ -73046,9 +74206,10 @@ } }, "metro-inspector-proxy": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-inspector-proxy/-/metro-inspector-proxy-0.76.7.tgz", - "integrity": "sha512-rNZ/6edTl/1qUekAhAbaFjczMphM50/UjtxiKulo6vqvgn/Mjd9hVqDvVYfAMZXqPvlusD88n38UjVYPkruLSg==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-inspector-proxy/-/metro-inspector-proxy-0.76.8.tgz", + "integrity": "sha512-Us5o5UEd4Smgn1+TfHX4LvVPoWVo9VsVMn4Ldbk0g5CQx3Gu0ygc/ei2AKPGTwsOZmKxJeACj7yMH2kgxQP/iw==", + "dev": true, "requires": { "connect": "^3.6.5", "debug": "^2.2.0", @@ -73061,6 +74222,7 @@ "version": "8.0.1", "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", "integrity": "sha512-BSeNnyus75C4//NQ9gQt1/csTXyo/8Sb+afLAkzAptFuMsod9HFokGNudZpi/oQV73hnVK+sR+5PVRMd+Dr7YQ==", + "dev": true, "requires": { "string-width": "^4.2.0", "strip-ansi": "^6.0.1", @@ -73071,6 +74233,7 @@ "version": "2.6.9", "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, "requires": { "ms": "2.0.0" } @@ -73078,23 +74241,27 @@ "ms": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" + "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", + "dev": true }, "ws": { "version": "7.5.9", "resolved": "https://registry.npmjs.org/ws/-/ws-7.5.9.tgz", "integrity": "sha512-F+P9Jil7UiSKSkppIiD94dN07AwvFixvLIj1Og1Rl9GGMuNipJnV9JzjD6XuqmAeiswGvUmNLjr5cFuXwNS77Q==", + "dev": true, "requires": {} }, "y18n": { "version": "5.0.8", "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", - "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==" + "integrity": "sha512-0pfFzegeDWJHJIAmTLRP2DwHjdF5s7jo9tuztdQxAhINCdvS+3nGINqPd00AphqJR/0LhANUS6/+7SCb98YOfA==", + "dev": true }, "yargs": { "version": "17.7.2", "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", + "dev": true, "requires": { "cliui": "^8.0.1", "escalade": "^3.1.1", @@ -73108,30 +74275,34 @@ "yargs-parser": { "version": "21.1.1", "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-21.1.1.tgz", - "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==" + "integrity": "sha512-tVpsJW7DdjecAiFpbIB1e3qxIQsE6NoPc5/eTdrbbIC4h0LVsWhnoa3g+m2HclBIujHzsxZ4VJVA+GUuc2/LBw==", + "dev": true } } }, "metro-minify-terser": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-minify-terser/-/metro-minify-terser-0.76.7.tgz", - "integrity": "sha512-FQiZGhIxCzhDwK4LxyPMLlq0Tsmla10X7BfNGlYFK0A5IsaVKNJbETyTzhpIwc+YFRT4GkFFwgo0V2N5vxO5HA==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-minify-terser/-/metro-minify-terser-0.76.8.tgz", + "integrity": "sha512-Orbvg18qXHCrSj1KbaeSDVYRy/gkro2PC7Fy2tDSH1c9RB4aH8tuMOIXnKJE+1SXxBtjWmQ5Yirwkth2DyyEZA==", + "dev": true, "requires": { "terser": "^5.15.0" } }, "metro-minify-uglify": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-minify-uglify/-/metro-minify-uglify-0.76.7.tgz", - "integrity": "sha512-FuXIU3j2uNcSvQtPrAJjYWHruPiQ+EpE++J9Z+VznQKEHcIxMMoQZAfIF2IpZSrZYfLOjVFyGMvj41jQMxV1Vw==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-minify-uglify/-/metro-minify-uglify-0.76.8.tgz", + "integrity": "sha512-6l8/bEvtVaTSuhG1FqS0+Mc8lZ3Bl4RI8SeRIifVLC21eeSDp4CEBUWSGjpFyUDfi6R5dXzYaFnSgMNyfxADiQ==", + "dev": true, "requires": { "uglify-es": "^3.1.9" } }, "metro-react-native-babel-preset": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-react-native-babel-preset/-/metro-react-native-babel-preset-0.76.7.tgz", - "integrity": "sha512-R25wq+VOSorAK3hc07NW0SmN8z9S/IR0Us0oGAsBcMZnsgkbOxu77Mduqf+f4is/wnWHc5+9bfiqdLnaMngiVw==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-react-native-babel-preset/-/metro-react-native-babel-preset-0.76.8.tgz", + "integrity": "sha512-Ptza08GgqzxEdK8apYsjTx2S8WDUlS2ilBlu9DR1CUcHmg4g3kOkFylZroogVAUKtpYQNYwAvdsjmrSdDNtiAg==", + "dev": true, "requires": { "@babel/core": "^7.20.0", "@babel/plugin-proposal-async-generator-functions": "^7.0.0", @@ -73175,31 +74346,34 @@ }, "dependencies": { "react-refresh": { - "version": "0.4.3" + "version": "0.4.3", + "dev": true } } }, "metro-react-native-babel-transformer": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-react-native-babel-transformer/-/metro-react-native-babel-transformer-0.76.7.tgz", - "integrity": "sha512-W6lW3J7y/05ph3c2p3KKJNhH0IdyxdOCbQ5it7aM2MAl0SM4wgKjaV6EYv9b3rHklpV6K3qMH37UKVcjMooWiA==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-react-native-babel-transformer/-/metro-react-native-babel-transformer-0.76.8.tgz", + "integrity": "sha512-3h+LfS1WG1PAzhq8QF0kfXjxuXetbY/lgz8vYMQhgrMMp17WM1DNJD0gjx8tOGYbpbBC1qesJ45KMS4o5TA73A==", + "dev": true, "requires": { "@babel/core": "^7.20.0", "babel-preset-fbjs": "^3.4.0", "hermes-parser": "0.12.0", - "metro-react-native-babel-preset": "0.76.7", + "metro-react-native-babel-preset": "0.76.8", "nullthrows": "^1.1.1" } }, "metro-resolver": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-resolver/-/metro-resolver-0.76.7.tgz", - "integrity": "sha512-pC0Wgq29HHIHrwz23xxiNgylhI8Rq1V01kQaJ9Kz11zWrIdlrH0ZdnJ7GC6qA0ErROG+cXmJ0rJb8/SW1Zp2IA==" + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-resolver/-/metro-resolver-0.76.8.tgz", + "integrity": "sha512-KccOqc10vrzS7ZhG2NSnL2dh3uVydarB7nOhjreQ7C4zyWuiW9XpLC4h47KtGQv3Rnv/NDLJYeDqaJ4/+140HQ==", + "dev": true }, "metro-runtime": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-runtime/-/metro-runtime-0.76.7.tgz", - "integrity": "sha512-MuWHubQHymUWBpZLwuKZQgA/qbb35WnDAKPo83rk7JRLIFPvzXSvFaC18voPuzJBt1V98lKQIonh6MiC9gd8Ug==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-runtime/-/metro-runtime-0.76.8.tgz", + "integrity": "sha512-XKahvB+iuYJSCr3QqCpROli4B4zASAYpkK+j3a0CJmokxCDNbgyI4Fp88uIL6rNaZfN0Mv35S0b99SdFXIfHjg==", "requires": { "@babel/runtime": "^7.0.0", "react-refresh": "^0.4.0" @@ -73213,16 +74387,16 @@ } }, "metro-source-map": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-source-map/-/metro-source-map-0.76.7.tgz", - "integrity": "sha512-Prhx7PeRV1LuogT0Kn5VjCuFu9fVD68eefntdWabrksmNY6mXK8pRqzvNJOhTojh6nek+RxBzZeD6MIOOyXS6w==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-source-map/-/metro-source-map-0.76.8.tgz", + "integrity": "sha512-Hh0ncPsHPVf6wXQSqJqB3K9Zbudht4aUtNpNXYXSxH+pteWqGAXnjtPsRAnCsCWl38wL0jYF0rJDdMajUI3BDw==", "requires": { "@babel/traverse": "^7.20.0", "@babel/types": "^7.20.0", "invariant": "^2.2.4", - "metro-symbolicate": "0.76.7", + "metro-symbolicate": "0.76.8", "nullthrows": "^1.1.1", - "ob1": "0.76.7", + "ob1": "0.76.8", "source-map": "^0.5.6", "vlq": "^1.0.0" }, @@ -73235,12 +74409,12 @@ } }, "metro-symbolicate": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-symbolicate/-/metro-symbolicate-0.76.7.tgz", - "integrity": "sha512-p0zWEME5qLSL1bJb93iq+zt5fz3sfVn9xFYzca1TJIpY5MommEaS64Va87lp56O0sfEIvh4307Oaf/ZzRjuLiQ==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-symbolicate/-/metro-symbolicate-0.76.8.tgz", + "integrity": "sha512-LrRL3uy2VkzrIXVlxoPtqb40J6Bf1mlPNmUQewipc3qfKKFgtPHBackqDy1YL0njDsWopCKcfGtFYLn0PTUn3w==", "requires": { "invariant": "^2.2.4", - "metro-source-map": "0.76.7", + "metro-source-map": "0.76.8", "nullthrows": "^1.1.1", "source-map": "^0.5.6", "through2": "^2.0.1", @@ -73255,9 +74429,10 @@ } }, "metro-transform-plugins": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-transform-plugins/-/metro-transform-plugins-0.76.7.tgz", - "integrity": "sha512-iSmnjVApbdivjuzb88Orb0JHvcEt5veVyFAzxiS5h0QB+zV79w6JCSqZlHCrbNOkOKBED//LqtKbFVakxllnNg==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-transform-plugins/-/metro-transform-plugins-0.76.8.tgz", + "integrity": "sha512-PlkGTQNqS51Bx4vuufSQCdSn2R2rt7korzngo+b5GCkeX5pjinPjnO2kNhQ8l+5bO0iUD/WZ9nsM2PGGKIkWFA==", + "dev": true, "requires": { "@babel/core": "^7.20.0", "@babel/generator": "^7.20.0", @@ -73267,21 +74442,22 @@ } }, "metro-transform-worker": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/metro-transform-worker/-/metro-transform-worker-0.76.7.tgz", - "integrity": "sha512-cGvELqFMVk9XTC15CMVzrCzcO6sO1lURfcbgjuuPdzaWuD11eEyocvkTX0DPiRjsvgAmicz4XYxVzgYl3MykDw==", + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/metro-transform-worker/-/metro-transform-worker-0.76.8.tgz", + "integrity": "sha512-mE1fxVAnJKmwwJyDtThildxxos9+DGs9+vTrx2ktSFMEVTtXS/bIv2W6hux1pqivqAfyJpTeACXHk5u2DgGvIQ==", + "dev": true, "requires": { "@babel/core": "^7.20.0", "@babel/generator": "^7.20.0", "@babel/parser": "^7.20.0", "@babel/types": "^7.20.0", "babel-preset-fbjs": "^3.4.0", - "metro": "0.76.7", - "metro-babel-transformer": "0.76.7", - "metro-cache": "0.76.7", - "metro-cache-key": "0.76.7", - "metro-source-map": "0.76.7", - "metro-transform-plugins": "0.76.7", + "metro": "0.76.8", + "metro-babel-transformer": "0.76.8", + "metro-cache": "0.76.8", + "metro-cache-key": "0.76.8", + "metro-source-map": "0.76.8", + "metro-transform-plugins": "0.76.8", "nullthrows": "^1.1.1" } }, @@ -74323,9 +75499,9 @@ "dev": true }, "ob1": { - "version": "0.76.7", - "resolved": "https://registry.npmjs.org/ob1/-/ob1-0.76.7.tgz", - "integrity": "sha512-BQdRtxxoUNfSoZxqeBGOyuT9nEYSn18xZHwGMb0mMVpn2NBcYbnyKY4BK2LIHRgw33CBGlUmE+KMaNvyTpLLtQ==" + "version": "0.76.8", + "resolved": "https://registry.npmjs.org/ob1/-/ob1-0.76.8.tgz", + "integrity": "sha512-dlBkJJV5M/msj9KYA9upc+nUWVwuOFFTbu28X6kZeGwcuW+JxaHSBZ70SYQnk5M+j5JbNLR6yKHmgW4M5E7X5g==" }, "object-assign": { "version": "4.1.1" @@ -75786,20 +76962,20 @@ } }, "react-native": { - "version": "0.72.3", - "resolved": "https://registry.npmjs.org/react-native/-/react-native-0.72.3.tgz", - "integrity": "sha512-QqISi+JVmCssNP2FlQ4MWhlc4O/I00MRE1/GClvyZ8h/6kdsyk/sOirkYdZqX3+DrJfI3q+OnyMnsyaXIQ/5tQ==", + "version": "0.72.4", + "resolved": "https://registry.npmjs.org/react-native/-/react-native-0.72.4.tgz", + "integrity": "sha512-+vrObi0wZR+NeqL09KihAAdVlQ9IdplwznJWtYrjnQ4UbCW6rkzZJebRsugwUneSOKNFaHFEo1uKU89HsgtYBg==", "requires": { "@jest/create-cache-key-function": "^29.2.1", - "@react-native-community/cli": "11.3.5", - "@react-native-community/cli-platform-android": "11.3.5", - "@react-native-community/cli-platform-ios": "11.3.5", + "@react-native-community/cli": "11.3.6", + "@react-native-community/cli-platform-android": "11.3.6", + "@react-native-community/cli-platform-ios": "11.3.6", "@react-native/assets-registry": "^0.72.0", "@react-native/codegen": "^0.72.6", "@react-native/gradle-plugin": "^0.72.11", "@react-native/js-polyfills": "^0.72.1", "@react-native/normalize-colors": "^0.72.0", - "@react-native/virtualized-lists": "^0.72.6", + "@react-native/virtualized-lists": "^0.72.8", "abort-controller": "^3.0.0", "anser": "^1.4.9", "base64-js": "^1.1.2", @@ -75810,8 +76986,8 @@ "jest-environment-node": "^29.2.1", "jsc-android": "^250231.0.0", "memoize-one": "^5.0.0", - "metro-runtime": "0.76.7", - "metro-source-map": "0.76.7", + "metro-runtime": "0.76.8", + "metro-source-map": "0.76.8", "mkdirp": "^0.5.1", "nullthrows": "^1.1.1", "pretty-format": "^26.5.2", @@ -76037,9 +77213,9 @@ } }, "react-native-google-places-autocomplete": { - "version": "git+ssh://git@github.com/Expensify/react-native-google-places-autocomplete.git#ee87343c3e827ff7818abc71b6bb04fcc1f120e0", - "integrity": "sha512-OJWCz4Epj1p8tyNImWNykAqpd/X1MkNCFPY0dSbgiTJGbW4J5T4bC0PIUQ+ExjxWpWjcFaielTLdoSz0HfeIpw==", - "from": "react-native-google-places-autocomplete@git+https://github.com/Expensify/react-native-google-places-autocomplete.git#ee87343c3e827ff7818abc71b6bb04fcc1f120e0", + "version": "git+ssh://git@github.com/Expensify/react-native-google-places-autocomplete.git#cef3ac29d9501091453136e1219e24c4ec9f9d76", + "integrity": "sha512-2z3ED8jOXasPTzBqvPwpG10LQsBArTRsYszmoz+TfqbgZrSBmP3c8rhaC//lx6Pvfs2r+KYWqJUrLf4mbCrjZw==", + "from": "react-native-google-places-autocomplete@git+https://github.com/Expensify/react-native-google-places-autocomplete.git#cef3ac29d9501091453136e1219e24c4ec9f9d76", "requires": { "lodash.debounce": "^4.0.8", "prop-types": "^15.7.2", @@ -76093,9 +77269,9 @@ } }, "react-native-onyx": { - "version": "1.0.77", - "resolved": "https://registry.npmjs.org/react-native-onyx/-/react-native-onyx-1.0.77.tgz", - "integrity": "sha512-HmeS1Pz/BkKNbYuhWULC9I0VRBDt8yadG0ZFIW6wuZ+VajhjD960qh7Il1+XzEBI6Vb4d7BZkPcad87ad1IEOQ==", + "version": "1.0.87", + "resolved": "https://registry.npmjs.org/react-native-onyx/-/react-native-onyx-1.0.87.tgz", + "integrity": "sha512-6mIhobSwpClDDGnJm9XEdjnpEdWfFesJ18J8Ifsb4tL6AVi+uxos5bnlZcOoMbtlUk3UozrgSyTjMfFrkD/aZA==", "requires": { "ascii-table": "0.0.9", "fast-equals": "^4.0.3", @@ -76156,9 +77332,9 @@ "requires": {} }, "react-native-reanimated": { - "version": "3.4.0", - "resolved": "https://registry.npmjs.org/react-native-reanimated/-/react-native-reanimated-3.4.0.tgz", - "integrity": "sha512-B5cZJseoIkYlZTRBRN0xuU1NBxUza/6GSHhiEBQfbOufWVlUMMcWUecIRVglW49l8d2wXbfCdQlNyVoFqmHkaQ==", + "version": "3.5.4", + "resolved": "https://registry.npmjs.org/react-native-reanimated/-/react-native-reanimated-3.5.4.tgz", + "integrity": "sha512-8we9LLDO1o4Oj9/DICeEJ2K1tjfqkJagqQUglxeUAkol/HcEJ6PGxIrpBcNryLqCDYEcu6FZWld/FzizBIw6bg==", "requires": { "@babel/plugin-transform-object-assign": "^7.16.7", "@babel/preset-typescript": "^7.16.7", @@ -76167,7 +77343,9 @@ }, "dependencies": { "convert-source-map": { - "version": "2.0.0" + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-2.0.0.tgz", + "integrity": "sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==" } } }, @@ -79055,7 +80233,9 @@ "dev": true }, "throat": { - "version": "5.0.0" + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/throat/-/throat-5.0.0.tgz", + "integrity": "sha512-fcwX4mndzpLQKBS1DVYhGAcYaYt7vsHNIvQV+WXMvnow5cgjPphq5CaayLaGsjRdSCKZFNGt7/GYAuXaNOiYCA==" }, "throttle-debounce": { "version": "3.0.1", @@ -79959,7 +81139,9 @@ "version": "1.2.8" }, "vlq": { - "version": "1.0.1" + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/vlq/-/vlq-1.0.1.tgz", + "integrity": "sha512-gQpnTgkubC6hQgdIcRdYGDSDc+SaujOdyesZQMv6JlfQee/9Mp0Qhnys6WxDWvQnL5WZdT7o2Ul187aSt0Rq+w==" }, "vm-browserify": { "version": "1.1.2" diff --git a/package.json b/package.json index 72574455719b..cd93f718679e 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "new.expensify", - "version": "1.3.71-5", + "version": "1.3.74-2", "author": "Expensify, Inc.", "homepage": "https://new.expensify.com", "description": "New Expensify is the next generation of Expensify: a reimagination of payments based atop a foundation of chat.", @@ -48,6 +48,7 @@ "symbolicate:android": "npx metro-symbolicate android/app/build/generated/sourcemaps/react/release/index.android.bundle.map", "symbolicate:ios": "npx metro-symbolicate main.jsbundle.map", "test:e2e": "node tests/e2e/testRunner.js --development", + "gh-actions-unused-styles": "./.github/scripts/findUnusedKeys.sh", "workflow-test": "./workflow_tests/scripts/runWorkflowTests.sh", "workflow-test:generate": "node workflow_tests/utils/preGenerateTest.js" }, @@ -61,9 +62,9 @@ "@formatjs/intl-pluralrules": "^5.2.2", "@gorhom/portal": "^1.0.14", "@invertase/react-native-apple-authentication": "^2.2.2", - "@oguzhnatly/react-native-image-manipulator": "github:Expensify/react-native-image-manipulator#5cdae3d4455b03a04c57f50be3863e2fe6c92c52", "@kie/act-js": "^2.0.1", "@kie/mock-github": "^1.0.0", + "@oguzhnatly/react-native-image-manipulator": "github:Expensify/react-native-image-manipulator#5cdae3d4455b03a04c57f50be3863e2fe6c92c52", "@onfido/react-native-sdk": "7.4.0", "@react-native-async-storage/async-storage": "^1.17.10", "@react-native-camera-roll/camera-roll": "5.4.0", @@ -81,9 +82,9 @@ "@react-navigation/stack": "6.3.16", "@react-ng/bounds-observer": "^0.2.1", "@rnmapbox/maps": "^10.0.11", + "@types/node": "^18.14.0", "@ua/react-native-airship": "^15.2.6", "awesome-phonenumber": "^5.4.0", - "@types/node": "^18.14.0", "babel-plugin-transform-remove-console": "^6.9.4", "babel-polyfill": "^6.26.0", "canvas-size": "^1.2.6", @@ -92,7 +93,7 @@ "date-fns-tz": "^2.0.0", "dom-serializer": "^0.2.2", "domhandler": "^4.3.0", - "expensify-common": "git+ssh://git@github.com/Expensify/expensify-common.git#35bff866a8d345b460ea6256f0a0f0a8a7f81086", + "expensify-common": "git+ssh://git@github.com/Expensify/expensify-common.git#1609f1848cc0c2528064519c3ea48b4953a708ee", "fbjs": "^3.0.2", "htmlparser2": "^7.2.0", "idb-keyval": "^6.2.1", @@ -113,7 +114,7 @@ "react-dom": "18.1.0", "react-map-gl": "^7.1.3", "react-error-boundary": "^4.0.11", - "react-native": "0.72.3", + "react-native": "0.72.4", "react-native-blob-util": "^0.17.3", "react-native-collapsible": "^1.6.0", "react-native-config": "^1.4.5", @@ -123,7 +124,7 @@ "react-native-fast-image": "^8.6.3", "react-native-fs": "^2.20.0", "react-native-gesture-handler": "2.12.0", - "react-native-google-places-autocomplete": "git+https://github.com/Expensify/react-native-google-places-autocomplete.git#ee87343c3e827ff7818abc71b6bb04fcc1f120e0", + "react-native-google-places-autocomplete": "git+https://github.com/Expensify/react-native-google-places-autocomplete.git#cef3ac29d9501091453136e1219e24c4ec9f9d76", "react-native-haptic-feedback": "^1.13.0", "react-native-image-pan-zoom": "^2.1.12", "react-native-image-picker": "^5.1.0", @@ -132,7 +133,7 @@ "react-native-linear-gradient": "^2.8.1", "react-native-localize": "^2.2.6", "react-native-modal": "^13.0.0", - "react-native-onyx": "1.0.77", + "react-native-onyx": "1.0.87", "react-native-pager-view": "^6.2.0", "react-native-pdf": "^6.7.1", "react-native-performance": "^5.1.0", @@ -141,7 +142,7 @@ "react-native-plaid-link-sdk": "^10.0.0", "react-native-qrcode-svg": "^6.2.0", "react-native-quick-sqlite": "^8.0.0-beta.2", - "react-native-reanimated": "3.4.0", + "react-native-reanimated": "3.5.4", "react-native-render-html": "6.3.1", "react-native-safe-area-context": "4.4.1", "react-native-screens": "3.21.0", @@ -181,7 +182,7 @@ "@octokit/plugin-paginate-rest": "3.1.0", "@octokit/plugin-throttling": "4.1.0", "@react-native-community/eslint-config": "3.0.0", - "@react-native/metro-config": "^0.72.9", + "@react-native/metro-config": "^0.72.11", "@react-navigation/devtools": "^6.0.10", "@storybook/addon-a11y": "^6.5.9", "@storybook/addon-essentials": "^7.0.0", @@ -232,7 +233,7 @@ "electron-builder": "24.6.4", "eslint": "^7.6.0", "eslint-config-airbnb-typescript": "^17.1.0", - "eslint-config-expensify": "^2.0.38", + "eslint-config-expensify": "^2.0.39", "eslint-config-prettier": "^8.8.0", "eslint-plugin-jest": "^24.1.0", "eslint-plugin-jsdoc": "^46.2.6", @@ -246,7 +247,7 @@ "jest-circus": "29.4.1", "jest-cli": "29.4.1", "jest-environment-jsdom": "^29.4.1", - "metro-react-native-babel-preset": "0.76.7", + "metro-react-native-babel-preset": "0.76.8", "mock-fs": "^4.13.0", "onchange": "^7.1.0", "portfinder": "^1.0.28", diff --git a/patches/react-native+0.72.3+001+initial.patch b/patches/react-native+0.72.4+001+initial.patch similarity index 100% rename from patches/react-native+0.72.3+001+initial.patch rename to patches/react-native+0.72.4+001+initial.patch diff --git a/patches/react-native+0.72.3+002+NumberOfLines.patch b/patches/react-native+0.72.4+002+NumberOfLines.patch similarity index 97% rename from patches/react-native+0.72.3+002+NumberOfLines.patch rename to patches/react-native+0.72.4+002+NumberOfLines.patch index 7d773297cb5f..75422f84708e 100644 --- a/patches/react-native+0.72.3+002+NumberOfLines.patch +++ b/patches/react-native+0.72.4+002+NumberOfLines.patch @@ -30,10 +30,10 @@ index 6f69329..d531bee 100644 maxLength: true, autoCapitalize: true, diff --git a/node_modules/react-native/Libraries/Components/TextInput/TextInput.d.ts b/node_modules/react-native/Libraries/Components/TextInput/TextInput.d.ts -index ff029fb..0835135 100644 +index 8badb2a..b19f197 100644 --- a/node_modules/react-native/Libraries/Components/TextInput/TextInput.d.ts +++ b/node_modules/react-native/Libraries/Components/TextInput/TextInput.d.ts -@@ -338,12 +338,6 @@ export interface TextInputAndroidProps { +@@ -347,12 +347,6 @@ export interface TextInputAndroidProps { */ inlineImagePadding?: number | undefined; @@ -46,7 +46,7 @@ index ff029fb..0835135 100644 /** * Sets the return key to the label. Use it instead of `returnKeyType`. * @platform android -@@ -654,11 +648,29 @@ export interface TextInputProps +@@ -663,11 +657,30 @@ export interface TextInputProps */ maxLength?: number | undefined; @@ -72,6 +72,7 @@ index ff029fb..0835135 100644 + * Use it with multiline set to true to be able to fill the lines. + */ + rows?: number | undefined; ++ + /** * Callback that is called when the text input is blurred @@ -147,10 +148,10 @@ index 7ed4579..b1d994e 100644 * If `true`, the text input obscures the text entered so that sensitive text * like passwords stay secure. The default value is `false`. Does not work with 'multiline={true}'. diff --git a/node_modules/react-native/Libraries/Components/TextInput/TextInput.js b/node_modules/react-native/Libraries/Components/TextInput/TextInput.js -index df89097..3b223ec 100644 +index 2127191..542fc06 100644 --- a/node_modules/react-native/Libraries/Components/TextInput/TextInput.js +++ b/node_modules/react-native/Libraries/Components/TextInput/TextInput.js -@@ -387,7 +387,6 @@ type AndroidProps = $ReadOnly<{| +@@ -390,7 +390,6 @@ type AndroidProps = $ReadOnly<{| /** * Sets the number of lines for a `TextInput`. Use it with multiline set to * `true` to be able to fill the lines. @@ -158,7 +159,7 @@ index df89097..3b223ec 100644 */ numberOfLines?: ?number, -@@ -400,10 +399,14 @@ type AndroidProps = $ReadOnly<{| +@@ -403,10 +402,14 @@ type AndroidProps = $ReadOnly<{| /** * Sets the number of rows for a `TextInput`. Use it with multiline set to * `true` to be able to fill the lines. @@ -174,7 +175,7 @@ index df89097..3b223ec 100644 /** * When `false`, it will prevent the soft keyboard from showing when the field is focused. * Defaults to `true`. -@@ -1066,6 +1069,9 @@ function InternalTextInput(props: Props): React.Node { +@@ -1069,6 +1072,9 @@ function InternalTextInput(props: Props): React.Node { accessibilityState, id, tabIndex, @@ -184,7 +185,7 @@ index df89097..3b223ec 100644 selection: propsSelection, ...otherProps } = props; -@@ -1422,6 +1428,8 @@ function InternalTextInput(props: Props): React.Node { +@@ -1427,6 +1433,8 @@ function InternalTextInput(props: Props): React.Node { focusable={tabIndex !== undefined ? !tabIndex : focusable} mostRecentEventCount={mostRecentEventCount} nativeID={id ?? props.nativeID} @@ -193,7 +194,7 @@ index df89097..3b223ec 100644 onBlur={_onBlur} onKeyPressSync={props.unstable_onKeyPressSync} onChange={_onChange} -@@ -1477,6 +1485,7 @@ function InternalTextInput(props: Props): React.Node { +@@ -1482,6 +1490,7 @@ function InternalTextInput(props: Props): React.Node { mostRecentEventCount={mostRecentEventCount} nativeID={id ?? props.nativeID} numberOfLines={props.rows ?? props.numberOfLines} @@ -549,7 +550,7 @@ index 190bc27..c2bcdc1 100644 : mEllipsizeLocation; setEllipsize(ellipsizeLocation); diff --git a/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/text/TextLayoutManager.java b/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/text/TextLayoutManager.java -index 561a2d0..017be13 100644 +index 561a2d0..9409cfc 100644 --- a/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/text/TextLayoutManager.java +++ b/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/text/TextLayoutManager.java @@ -18,6 +18,7 @@ import android.text.SpannableStringBuilder; @@ -568,7 +569,7 @@ index 561a2d0..017be13 100644 private static final LruCache sSpannableCache = new LruCache<>(spannableCacheSize); private static final ConcurrentHashMap sTagToSpannableCache = -@@ -385,6 +387,47 @@ public class TextLayoutManager { +@@ -385,6 +387,48 @@ public class TextLayoutManager { ? paragraphAttributes.getInt(MAXIMUM_NUMBER_OF_LINES_KEY) : UNSET; @@ -612,12 +613,13 @@ index 561a2d0..017be13 100644 + if (numberOfLines != UNSET && numberOfLines != 0) { + maximumNumberOfLines = numberOfLines; + } ++ + int calculatedLineCount = maximumNumberOfLines == UNSET || maximumNumberOfLines == 0 ? layout.getLineCount() diff --git a/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/text/TextLayoutManagerMapBuffer.java b/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/text/TextLayoutManagerMapBuffer.java -index 0d118f0..f29f069 100644 +index 0d118f0..0ae44b7 100644 --- a/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/text/TextLayoutManagerMapBuffer.java +++ b/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/text/TextLayoutManagerMapBuffer.java @@ -18,6 +18,7 @@ import android.text.SpannableStringBuilder; @@ -636,7 +638,7 @@ index 0d118f0..f29f069 100644 private static final boolean ENABLE_MEASURE_LOGGING = ReactBuildConfig.DEBUG && false; -@@ -399,6 +401,46 @@ public class TextLayoutManagerMapBuffer { +@@ -399,6 +401,47 @@ public class TextLayoutManagerMapBuffer { ? paragraphAttributes.getInt(PA_KEY_MAX_NUMBER_OF_LINES) : UNSET; @@ -679,15 +681,16 @@ index 0d118f0..f29f069 100644 + if (numberOfLines != UNSET && numberOfLines != 0) { + maximumNumberOfLines = numberOfLines; + } ++ + int calculatedLineCount = maximumNumberOfLines == UNSET || maximumNumberOfLines == 0 ? layout.getLineCount() diff --git a/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditText.java b/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditText.java -index 1b5e0f4..67d0b73 100644 +index ced37be..ef2f321 100644 --- a/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditText.java +++ b/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditText.java -@@ -483,7 +483,13 @@ public class ReactEditText extends AppCompatEditText +@@ -548,7 +548,13 @@ public class ReactEditText extends AppCompatEditText * href='https://android.googlesource.com/platform/frameworks/base/+/jb-release/core/java/android/widget/TextView.java'>TextView.java} */ if (isMultiline()) { @@ -807,10 +810,10 @@ index f5f87c6..b7d1e90 100644 attributes.ellipsizeMode, attributes.textBreakStrategy, diff --git a/node_modules/react-native/ReactCommon/react/renderer/attributedstring/conversions.h b/node_modules/react-native/ReactCommon/react/renderer/attributedstring/conversions.h -index 8687b89..26379f4 100644 +index 8687b89..eab75f4 100644 --- a/node_modules/react-native/ReactCommon/react/renderer/attributedstring/conversions.h +++ b/node_modules/react-native/ReactCommon/react/renderer/attributedstring/conversions.h -@@ -835,12 +835,18 @@ inline ParagraphAttributes convertRawProp( +@@ -835,10 +835,16 @@ inline ParagraphAttributes convertRawProp( ParagraphAttributes const &defaultParagraphAttributes) { auto paragraphAttributes = ParagraphAttributes{}; @@ -819,19 +822,15 @@ index 8687b89..26379f4 100644 context, rawProps, "numberOfLines", -- sourceParagraphAttributes.maximumNumberOfLines, -- defaultParagraphAttributes.maximumNumberOfLines); + sourceParagraphAttributes.numberOfLines, + defaultParagraphAttributes.numberOfLines); + paragraphAttributes.maximumNumberOfLines = convertRawProp( -+ context, -+ rawProps, -+ "maximumNumberOfLines", -+ sourceParagraphAttributes.maximumNumberOfLines, -+ defaultParagraphAttributes.maximumNumberOfLines); ++ context, ++ rawProps, ++ "maximumNumberOfLines", + sourceParagraphAttributes.maximumNumberOfLines, + defaultParagraphAttributes.maximumNumberOfLines); paragraphAttributes.ellipsizeMode = convertRawProp( - context, - rawProps, @@ -913,6 +919,7 @@ inline std::string toString(AttributedString::Range const &range) { inline folly::dynamic toDynamic( const ParagraphAttributes ¶graphAttributes) { @@ -853,7 +852,7 @@ index 8687b89..26379f4 100644 PA_KEY_HYPHENATION_FREQUENCY, toString(paragraphAttributes.android_hyphenationFrequency)); + builder.putInt( -+ PA_KEY_NUMBER_OF_LINES, paragraphAttributes.numberOfLines); ++ PA_KEY_NUMBER_OF_LINES, paragraphAttributes.numberOfLines); return builder.build(); } @@ -914,15 +913,15 @@ index ba39ebb..ead28e3 100644 std::string textBreakStrategy{}; SharedColor underlineColorAndroid{}; diff --git a/node_modules/react-native/ReactCommon/react/renderer/textlayoutmanager/platform/ios/react/renderer/textlayoutmanager/RCTTextLayoutManager.mm b/node_modules/react-native/ReactCommon/react/renderer/textlayoutmanager/platform/ios/react/renderer/textlayoutmanager/RCTTextLayoutManager.mm -index 368c334..2a98ad0 100644 +index 368c334..a1bb33e 100644 --- a/node_modules/react-native/ReactCommon/react/renderer/textlayoutmanager/platform/ios/react/renderer/textlayoutmanager/RCTTextLayoutManager.mm +++ b/node_modules/react-native/ReactCommon/react/renderer/textlayoutmanager/platform/ios/react/renderer/textlayoutmanager/RCTTextLayoutManager.mm -@@ -244,26 +244,50 @@ - (void)getRectWithAttributedString:(AttributedString)attributedString +@@ -244,26 +244,51 @@ - (void)getRectWithAttributedString:(AttributedString)attributedString #pragma mark - Private -- (NSTextStorage *)_textStorageForNSAttributesString:(NSAttributedString *)attributedString -+- (NSTextStorage *)_textStorageForNSAttributesString:(NSAttributedString *)inputAttributedString +++- (NSTextStorage *)_textStorageForNSAttributesString:(NSAttributedString *)inputAttributedString paragraphAttributes:(ParagraphAttributes)paragraphAttributes size:(CGSize)size { @@ -950,7 +949,6 @@ index 368c334..2a98ad0 100644 - ? RCTNSLineBreakModeFromEllipsizeMode(paragraphAttributes.ellipsizeMode) - : NSLineBreakByClipping; - textContainer.maximumNumberOfLines = paragraphAttributes.maximumNumberOfLines; -+ + [attributedString insertAttributedString:[[NSAttributedString alloc] initWithString:newLines attributes:attributesOfFirstCharacter] atIndex:0]; + } + @@ -959,7 +957,7 @@ index 368c334..2a98ad0 100644 NSLayoutManager *layoutManager = [NSLayoutManager new]; layoutManager.usesFontLeading = NO; [layoutManager addTextContainer:textContainer]; -- + - NSTextStorage *textStorage = [[NSTextStorage alloc] initWithAttributedString:attributedString]; + NSTextStorage *textStorage = [NSTextStorage new]; @@ -973,6 +971,7 @@ index 368c334..2a98ad0 100644 + textContainer.maximumNumberOfLines = paragraphAttributes.maximumNumberOfLines; + + [textStorage replaceCharactersInRange:(NSRange){0, textStorage.length} withAttributedString:attributedString]; ++ + if (paragraphAttributes.adjustsFontSizeToFit) { CGFloat minimumFontSize = !isnan(paragraphAttributes.minimumFontSize) ? paragraphAttributes.minimumFontSize : 4.0; diff --git a/patches/react-native+0.72.3+003+VerticalScrollBarPosition.patch b/patches/react-native+0.72.4+003+VerticalScrollBarPosition.patch similarity index 76% rename from patches/react-native+0.72.3+003+VerticalScrollBarPosition.patch rename to patches/react-native+0.72.4+003+VerticalScrollBarPosition.patch index 1cf8f6de54fb..e6ed0d4f79a3 100644 --- a/patches/react-native+0.72.3+003+VerticalScrollBarPosition.patch +++ b/patches/react-native+0.72.4+003+VerticalScrollBarPosition.patch @@ -1,12 +1,11 @@ diff --git a/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewManager.java b/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewManager.java -index 46e0ccf..53293a4 100644 +index 33658e7..31c20c0 100644 --- a/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewManager.java +++ b/node_modules/react-native/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewManager.java -@@ -379,4 +379,15 @@ public class ReactScrollViewManager extends ViewGroupManager - public void setScrollEventThrottle(ReactScrollView view, int scrollEventThrottle) { +@@ -381,6 +381,17 @@ public class ReactScrollViewManager extends ViewGroupManager view.setScrollEventThrottle(scrollEventThrottle); } -+ + + @ReactProp(name = "verticalScrollbarPosition") + public void setVerticalScrollbarPosition(ReactScrollView view, String position) { + if ("right".equals(position)) { @@ -17,4 +16,7 @@ index 46e0ccf..53293a4 100644 + view.setVerticalScrollbarPosition(View.SCROLLBAR_POSITION_DEFAULT); + } + } - } ++ + @ReactProp(name = "isInvertedVirtualizedList") + public void setIsInvertedVirtualizedList(ReactScrollView view, boolean applyFix) { + // Usually when inverting the scroll view we are using scaleY: -1 on the list diff --git a/patches/react-native+0.72.3+004+ModalKeyboardFlashing.patch b/patches/react-native+0.72.4+004+ModalKeyboardFlashing.patch similarity index 100% rename from patches/react-native+0.72.3+004+ModalKeyboardFlashing.patch rename to patches/react-native+0.72.4+004+ModalKeyboardFlashing.patch diff --git a/patches/react-native-image-picker+5.1.0.patch b/patches/react-native-image-picker+5.1.0.patch new file mode 100644 index 000000000000..0defc430e669 --- /dev/null +++ b/patches/react-native-image-picker+5.1.0.patch @@ -0,0 +1,133 @@ +diff --git a/node_modules/react-native-image-picker/android/src/main/java/com/imagepicker/ImagePickerModuleImpl.java b/node_modules/react-native-image-picker/android/src/main/java/com/imagepicker/ImagePickerModuleImpl.java +index 89b69a8..d86ab1e 100644 +--- a/node_modules/react-native-image-picker/android/src/main/java/com/imagepicker/ImagePickerModuleImpl.java ++++ b/node_modules/react-native-image-picker/android/src/main/java/com/imagepicker/ImagePickerModuleImpl.java +@@ -29,6 +29,120 @@ public class ImagePickerModuleImpl implements ActivityEventListener { + public static final int REQUEST_LAUNCH_VIDEO_CAPTURE = 13002; + public static final int REQUEST_LAUNCH_LIBRARY = 13003; + ++ // Prevent svg images from being selected as they are not supported (Image component does not support them) ++ // and also because iOS does not allow them to be selected (for consistency). ++ // Since, we can't exclude a mime type, we instead allow all image mime types except 'image/svg+xml'. ++ // Image mime types are generated by merging the Android image mime type support and the IANA media-types lists. ++ // https://android.googlesource.com/platform/external/mime-support/+/main/mime.types#636 ++ // https://www.iana.org/assignments/media-types/media-types.xhtml#image ++ private static final String[] ALLOWED_IMAGE_MIME_TYPES = { ++ "image/aces", ++ "image/apng", ++ "image/avci", ++ "image/avcs", ++ "image/avif", ++ "image/bmp", ++ "image/cgm", ++ "image/dicom-rle", ++ "image/dpx", ++ "image/emf", ++ "image/example", ++ "image/fits", ++ "image/g3fax", ++ "image/gif", ++ "image/heic-sequence", ++ "image/heic", ++ "image/heif-sequence", ++ "image/heif", ++ "image/hej2k", ++ "image/hsj2", ++ "image/ief", ++ "image/j2c", ++ "image/jls", ++ "image/jp2", ++ "image/jpeg", ++ "image/jph", ++ "image/jphc", ++ "image/jpm", ++ "image/jpx", ++ "image/jxr", ++ "image/jxrA", ++ "image/jxrS", ++ "image/jxs", ++ "image/jxsc", ++ "image/jxsi", ++ "image/jxss", ++ "image/ktx", ++ "image/ktx2", ++ "image/naplps", ++ "image/pcx", ++ "image/png", ++ "image/prs.btif", ++ "image/prs.pti", ++ "image/pwg-raster", ++ // "image/svg+xml", ++ "image/t38", ++ "image/tiff-fx", ++ "image/tiff", ++ "image/vnd.adobe.photoshop", ++ "image/vnd.airzip.accelerator.azv", ++ "image/vnd.cns.inf2", ++ "image/vnd.dece.graphic", ++ "image/vnd.djvu", ++ "image/vnd.dvb.subtitle", ++ "image/vnd.dwg", ++ "image/vnd.dxf", ++ "image/vnd.fastbidsheet", ++ "image/vnd.fpx", ++ "image/vnd.fst", ++ "image/vnd.fujixerox.edmics-mmr", ++ "image/vnd.fujixerox.edmics-rlc", ++ "image/vnd.globalgraphics.pgb", ++ "image/vnd.microsoft.icon", ++ "image/vnd.mix", ++ "image/vnd.mozilla.apng", ++ "image/vnd.ms-modi", ++ "image/vnd.net-fpx", ++ "image/vnd.pco.b16", ++ "image/vnd.radiance", ++ "image/vnd.sealed.png", ++ "image/vnd.sealedmedia.softseal.gif", ++ "image/vnd.sealedmedia.softseal.jpg", ++ "image/vnd.svf", ++ "image/vnd.tencent.tap", ++ "image/vnd.valve.source.texture", ++ "image/vnd.wap.wbmp", ++ "image/vnd.xiff", ++ "image/vnd.zbrush.pcx", ++ "image/webp", ++ "image/wmf", ++ "image/x-canon-cr2", ++ "image/x-canon-crw", ++ "image/x-cmu-raster", ++ "image/x-coreldraw", ++ "image/x-coreldrawpattern", ++ "image/x-coreldrawtemplate", ++ "image/x-corelphotopaint", ++ "image/x-emf", ++ "image/x-epson-erf", ++ "image/x-icon", ++ "image/x-jg", ++ "image/x-jng", ++ "image/x-ms-bmp", ++ "image/x-nikon-nef", ++ "image/x-olympus-orf", ++ "image/x-photoshop", ++ "image/x-portable-anymap", ++ "image/x-portable-bitmap", ++ "image/x-portable-graymap", ++ "image/x-portable-pixmap", ++ "image/x-rgb", ++ "image/x-wmf", ++ "image/x-xbitmap", ++ "image/x-xpixmap", ++ "image/x-xwindowdump", ++ }; ++ + private Uri fileUri; + + private ReactApplicationContext reactContext; +@@ -148,6 +262,7 @@ public class ImagePickerModuleImpl implements ActivityEventListener { + + if (isPhoto) { + libraryIntent.setType("image/*"); ++ libraryIntent.putExtra(Intent.EXTRA_MIME_TYPES, this.ALLOWED_IMAGE_MIME_TYPES); + } else if (isVideo) { + libraryIntent.setType("video/*"); + } else if (Build.VERSION.SDK_INT < Build.VERSION_CODES.TIRAMISU) { diff --git a/src/CONST.ts b/src/CONST.ts index 762186439cec..4d216285bc50 100755 --- a/src/CONST.ts +++ b/src/CONST.ts @@ -123,8 +123,6 @@ const CONST = { }, }, - RIGHT_MODAL_BACKGROUND_OVERLAY_OPACITY: 0.4, - NEW_EXPENSIFY_URL: ACTIVE_EXPENSIFY_URL, APP_DOWNLOAD_LINKS: { ANDROID: `https://play.google.com/store/apps/details?id=${ANDROID_PACKAGE_NAME}`, @@ -736,7 +734,7 @@ const CONST = { }, DEFAULT_TIME_ZONE: {automatic: true, selected: 'America/Los_Angeles'}, DEFAULT_ACCOUNT_DATA: {errors: null, success: '', isLoading: false}, - DEFAULT_CLOSE_ACCOUNT_DATA: {errors: {}, success: '', isLoading: false}, + DEFAULT_CLOSE_ACCOUNT_DATA: {errors: null, success: '', isLoading: false}, FORMS: { LOGIN_FORM: 'LoginForm', VALIDATE_CODE_FORM: 'ValidateCodeForm', @@ -757,6 +755,9 @@ const CONST = { // 6 numeric digits VALIDATE_CODE_REGEX_STRING: /^\d{6}$/, + // 8 alphanumeric characters + RECOVERY_CODE_REGEX_STRING: /^[a-zA-Z0-9]{8}$/, + // The server has a WAF (Web Application Firewall) which will strip out HTML/XML tags using this regex pattern. // It's copied here so that the same regex pattern can be used in form validations to be consistent with the server. VALIDATE_FOR_HTML_TAG_REGEX: /<([^>\s]+)(?:[^>]*?)>/g, @@ -792,6 +793,10 @@ const CONST = { INVISIBLE_CODEPOINTS: ['fe0f', '200d', '2066'], + UNICODE: { + LTR: '\u2066', + }, + TOOLTIP_MAX_LINES: 3, LOGIN_TYPE: { @@ -802,6 +807,8 @@ const CONST = { MAGIC_CODE_LENGTH: 6, MAGIC_CODE_EMPTY_CHAR: ' ', + RECOVERY_CODE_LENGTH: 8, + KEYBOARD_TYPE: { PHONE_PAD: 'phone-pad', NUMBER_PAD: 'number-pad', @@ -1026,7 +1033,6 @@ const CONST = { }, PAYMENT_METHODS: { - PAYPAL: 'payPalMe', DEBIT_CARD: 'debitCard', BANK_ACCOUNT: 'bankAccount', }, @@ -1042,7 +1048,6 @@ const CONST = { PAYMENT_TYPE: { ELSEWHERE: 'Elsewhere', EXPENSIFY: 'Expensify', - PAYPAL_ME: 'PayPal.me', VBBA: 'ACH', }, MONEY_REQUEST_TYPE: { @@ -1138,6 +1143,7 @@ const CONST = { DISTANCE_UNIT_KILOMETERS: 'km', MILEAGE_IRS_RATE: 0.655, DEFAULT_RATE: 'Default Rate', + RATE_DECIMALS: 3, }, TERMS: { @@ -1156,6 +1162,7 @@ const CONST = { }, AVATAR_SIZE: { + XLARGE: 'xlarge', LARGE: 'large', MEDIUM: 'medium', DEFAULT: 'default', @@ -1201,7 +1208,6 @@ const CONST = { CARD_NUMBER: /^[0-9]{15,16}$/, CARD_SECURITY_CODE: /^[0-9]{3,4}$/, CARD_EXPIRATION_DATE: /^(0[1-9]|1[0-2])([^0-9])?([0-9]{4}|([0-9]{2}))$/, - PAYPAL_ME_USERNAME: /^[a-zA-Z0-9]{1,20}$/, ROOM_NAME: /^#[a-z0-9à-ÿ-]{1,80}$/, // eslint-disable-next-line max-len, no-misleading-character-class @@ -1223,7 +1229,7 @@ const CONST = { SPECIAL_CHAR_OR_EMOJI: // eslint-disable-next-line no-misleading-character-class - /[\n\s,/?"{}[\]()&^%\\;`$=#<>!*\p{Extended_Pictographic}\u200d\u{1f1e6}-\u{1f1ff}\u{1f3fb}-\u{1f3ff}\u{e0020}-\u{e007f}\u20E3\uFE0F]|[#*0-9]\uFE0F?\u20E3/gu, + /[\n\s,/?"{}[\]()&_~^%\\;`$=#<>!*\p{Extended_Pictographic}\u200d\u{1f1e6}-\u{1f1ff}\u{1f3fb}-\u{1f3ff}\u{e0020}-\u{e007f}\u20E3\uFE0F]|[#*0-9]\uFE0F?\u20E3/gu, SPACE_OR_EMOJI: // eslint-disable-next-line no-misleading-character-class @@ -1305,9 +1311,9 @@ const CONST = { }, // Auth limit is 60k for the column but we store edits and other metadata along the html so let's use a lower limit to accommodate for it. - MAX_COMMENT_LENGTH: 15000, + MAX_COMMENT_LENGTH: 10000, - // Furthermore, applying markup is very resource-consuming, so let's set a slightly lower limit for that + // Use the same value as MAX_COMMENT_LENGTH to ensure the entire comment is parsed. Note that applying markup is very resource-consuming. MAX_MARKUP_LENGTH: 10000, MAX_THREAD_REPLIES_PREVIEW: 99, @@ -1351,6 +1357,9 @@ const CONST = { DATE: 'date', DESCRIPTION: 'description', MERCHANT: 'merchant', + CATEGORY: 'category', + RECEIPT: 'receipt', + TAG: 'tag', }, FOOTER: { EXPENSE_MANAGEMENT_URL: `${USE_EXPENSIFY_URL}/expense-management`, @@ -2532,32 +2541,6 @@ const CONST = { SEARCH_ISSUES: 'https://github.com/Expensify/App/issues', }, - PAYPAL_SUPPORTED_CURRENCIES: [ - 'AUD', - 'BRL', - 'CAD', - 'CZK', - 'DKK', - 'EUR', - 'HKD', - 'HUF', - 'ILS', - 'JPY', - 'MYR', - 'MXN', - 'TWD', - 'NZD', - 'NOK', - 'PHP', - 'PLN', - 'GBP', - 'RUB', - 'SGD', - 'SEK', - 'CHF', - 'THB', - 'USD', - ], CONCIERGE_TRAVEL_URL: 'https://community.expensify.com/discussion/7066/introducing-concierge-travel', SCREEN_READER_STATES: { ALL: 'all', @@ -2657,6 +2640,7 @@ const CONST = { INDENTS: ' ', PARENT_CHILD_SEPARATOR: ': ', CATEGORY_LIST_THRESHOLD: 8, + TAG_LIST_THRESHOLD: 8, DEMO_PAGES: { SAASTR: 'SaaStrDemoSetup', SBE: 'SbeDemoSetup', @@ -2672,6 +2656,15 @@ const CONST = { HTTPS: 'https', PUSHER: 'pusher', }, + EVENTS: { + SCROLLING: 'scrolling', + }, + HORIZONTAL_SPACER: { + DEFAULT_BORDER_BOTTOM_WIDTH: 1, + DEFAULT_MARGIN_VERTICAL: 8, + HIDDEN_MARGIN_VERTICAL: 0, + HIDDEN_BORDER_BOTTOM_WIDTH: 0, + }, } as const; export default CONST; diff --git a/src/Expensify.js b/src/Expensify.js index fba65e42c06c..9e6ae1ff27b4 100644 --- a/src/Expensify.js +++ b/src/Expensify.js @@ -99,7 +99,9 @@ function Expensify(props) { const [hasAttemptedToOpenPublicRoom, setAttemptedToOpenPublicRoom] = useState(false); useEffect(() => { - if (props.isCheckingPublicRoom) return; + if (props.isCheckingPublicRoom) { + return; + } setAttemptedToOpenPublicRoom(true); }, [props.isCheckingPublicRoom]); diff --git a/src/ONYXKEYS.ts b/src/ONYXKEYS.ts index 6eb795befe3c..6649a33fe15e 100755 --- a/src/ONYXKEYS.ts +++ b/src/ONYXKEYS.ts @@ -1,4 +1,5 @@ import {ValueOf} from 'type-fest'; +import {OnyxUpdate} from 'react-native-onyx'; import DeepValueOf from './types/utils/DeepValueOf'; import * as OnyxTypes from './types/onyx'; import CONST from './CONST'; @@ -88,9 +89,6 @@ const ONYXKEYS = { BETAS: 'betas', /** NVP keys - * Contains the user's payPalMe data */ - PAYPAL: 'paypal', - /** Contains the user preference for the LHN priority mode */ NVP_PRIORITY_MODE: 'nvp_priorityMode', @@ -172,6 +170,9 @@ const ONYXKEYS = { /** Is report data loading? */ IS_LOADING_REPORT_DATA: 'isLoadingReportData', + /** Is report data loading? */ + IS_LOADING_APP: 'isLoadingApp', + /** Is Keyboard shortcuts modal open? */ IS_SHORTCUTS_MODAL_OPEN: 'isShortcutsModalOpen', @@ -248,6 +249,7 @@ const ONYXKEYS = { REPORT_DRAFT_COMMENT_NUMBER_OF_LINES: 'reportDraftCommentNumberOfLines_', REPORT_IS_COMPOSER_FULL_SIZE: 'reportIsComposerFullSize_', REPORT_USER_IS_TYPING: 'reportUserIsTyping_', + REPORT_USER_IS_LEAVING_ROOM: 'reportUserIsLeavingRoom_', SECURITY_GROUP: 'securityGroup_', TRANSACTION: 'transactions_', @@ -281,7 +283,6 @@ const ONYXKEYS = { MONEY_REQUEST_AMOUNT_FORM: 'moneyRequestAmountForm', MONEY_REQUEST_DATE_FORM: 'moneyRequestCreatedForm', NEW_CONTACT_METHOD_FORM: 'newContactMethodForm', - PAYPAL_FORM: 'payPalForm', WAYPOINT_FORM: 'waypointForm', WAYPOINT_FORM_DRAFT: 'waypointFormDraft', SETTINGS_STATUS_SET_FORM: 'settingsStatusSetForm', @@ -305,7 +306,7 @@ type OnyxValues = { [ONYXKEYS.DEVICE_ID]: string; [ONYXKEYS.IS_SIDEBAR_LOADED]: boolean; [ONYXKEYS.PERSISTED_REQUESTS]: OnyxTypes.Request[]; - [ONYXKEYS.QUEUED_ONYX_UPDATES]: OnyxTypes.QueuedOnyxUpdates; + [ONYXKEYS.QUEUED_ONYX_UPDATES]: OnyxUpdate[]; [ONYXKEYS.CURRENT_DATE]: string; [ONYXKEYS.CREDENTIALS]: OnyxTypes.Credentials; [ONYXKEYS.IOU]: OnyxTypes.IOU; @@ -324,12 +325,11 @@ type OnyxValues = { [ONYXKEYS.LOGIN_LIST]: OnyxTypes.Login; [ONYXKEYS.SESSION]: OnyxTypes.Session; [ONYXKEYS.BETAS]: OnyxTypes.Beta[]; - [ONYXKEYS.PAYPAL]: OnyxTypes.Paypal; [ONYXKEYS.NVP_PRIORITY_MODE]: ValueOf; [ONYXKEYS.NVP_BLOCKED_FROM_CONCIERGE]: OnyxTypes.BlockedFromConcierge; [ONYXKEYS.NVP_PRIVATE_PUSH_NOTIFICATION_ID]: string; [ONYXKEYS.NVP_LAST_PAYMENT_METHOD]: Record; - [ONYXKEYS.NVP_RECENT_WAYPOINTS]: OnyxTypes.RecentWaypoints[]; + [ONYXKEYS.NVP_RECENT_WAYPOINTS]: OnyxTypes.RecentWaypoint[]; [ONYXKEYS.PUSH_NOTIFICATIONS_ENABLED]: boolean; [ONYXKEYS.PLAID_DATA]: OnyxTypes.PlaidData; [ONYXKEYS.IS_PLAID_DISABLED]: boolean; @@ -363,7 +363,6 @@ type OnyxValues = { [ONYXKEYS.LAST_OPENED_PUBLIC_ROOM_ID]: string; [ONYXKEYS.PREFERRED_THEME]: ValueOf; [ONYXKEYS.IS_USING_MEMORY_ONLY_KEYS]: boolean; - [ONYXKEYS.RECEIPT_MODAL]: OnyxTypes.ReceiptModal; [ONYXKEYS.MAPBOX_ACCESS_TOKEN]: OnyxTypes.MapboxAccessToken; [ONYXKEYS.ONYX_UPDATES_FROM_SERVER]: OnyxTypes.OnyxUpdatesFromServer; [ONYXKEYS.ONYX_UPDATES_LAST_UPDATE_ID_APPLIED_TO_CLIENT]: number; @@ -388,6 +387,7 @@ type OnyxValues = { [ONYXKEYS.COLLECTION.REPORT_DRAFT_COMMENT_NUMBER_OF_LINES]: number; [ONYXKEYS.COLLECTION.REPORT_IS_COMPOSER_FULL_SIZE]: boolean; [ONYXKEYS.COLLECTION.REPORT_USER_IS_TYPING]: boolean; + [ONYXKEYS.COLLECTION.REPORT_USER_IS_LEAVING_ROOM]: boolean; [ONYXKEYS.COLLECTION.SECURITY_GROUP]: OnyxTypes.SecurityGroup; [ONYXKEYS.COLLECTION.TRANSACTION]: OnyxTypes.Transaction; [ONYXKEYS.COLLECTION.POLICY_RECENTLY_USED_TAGS]: OnyxTypes.RecentlyUsedTags; @@ -416,7 +416,6 @@ type OnyxValues = { [ONYXKEYS.FORMS.MONEY_REQUEST_DATE_FORM]: OnyxTypes.Form; [ONYXKEYS.FORMS.MONEY_REQUEST_DATE_FORM]: OnyxTypes.Form; [ONYXKEYS.FORMS.NEW_CONTACT_METHOD_FORM]: OnyxTypes.Form; - [ONYXKEYS.FORMS.PAYPAL_FORM]: OnyxTypes.Form; [ONYXKEYS.FORMS.WAYPOINT_FORM]: OnyxTypes.Form; [ONYXKEYS.FORMS.WAYPOINT_FORM_DRAFT]: OnyxTypes.Form; [ONYXKEYS.FORMS.SETTINGS_STATUS_SET_FORM]: OnyxTypes.Form; diff --git a/src/ROUTES.ts b/src/ROUTES.ts index 9459708c893b..7f514e1a3645 100644 --- a/src/ROUTES.ts +++ b/src/ROUTES.ts @@ -1,35 +1,50 @@ import {ValueOf} from 'type-fest'; -import * as Url from './libs/Url'; import CONST from './CONST'; /** * This is a file containing constants for all of the routes we want to be able to go to */ -type ParseReportRouteParams = { - reportID: string; - isSubReportPageRoute: boolean; -}; +// prettier-ignore +export default { + HOME: '', + /** This is a utility route used to go to the user's concierge chat, or the sign-in page if the user's not authenticated */ + CONCIERGE: 'concierge', + FLAG_COMMENT: {route: 'flag/:reportID/:reportActionID', getRoute: (reportID: string, reportActionID: string) => `flag/${reportID}/${reportActionID}`}, + SEARCH: 'search', + DETAILS: {route: 'details', getRoute: (login: string) => `details?login=${encodeURIComponent(login)}`}, + PROFILE: { + route: 'a/:accountID', + getRoute: (accountID: string | number, backTo = '') => { + const backToParam = backTo ? `?backTo=${encodeURIComponent(backTo)}` : ''; + return `a/${accountID}${backToParam}`; + }, + }, -const REPORT = 'r'; -const IOU_REQUEST = 'request/new'; -const IOU_SEND = 'send/new'; -const NEW_TASK = 'new/task'; -const SETTINGS_PERSONAL_DETAILS = 'settings/profile/personal-details'; -const SETTINGS_CONTACT_METHODS = 'settings/profile/contact-methods'; -const SETTINGS_STATUS = 'settings/profile/status'; -const SETTINGS_STATUS_SET = 'settings/profile/status/set'; + TRANSITION_BETWEEN_APPS: 'transition', + VALIDATE_LOGIN: 'v/:accountID/:validateCode', + GET_ASSISTANCE: {route: 'get-assistance/:taskID', getRoute: (taskID: string) => `get-assistance/${taskID}`}, + UNLINK_LOGIN: 'u/:accountID/:validateCode', + APPLE_SIGN_IN: 'sign-in-with-apple', + GOOGLE_SIGN_IN: 'sign-in-with-google', + DESKTOP_SIGN_IN_REDIRECT: 'desktop-signin-redirect', + // This is a special validation URL that will take the user to /workspace/new after validation. This is used + // when linking users from e.com in order to share a session in this app. + ENABLE_PAYMENTS: 'enable-payments', + WALLET_STATEMENT_WITH_DATE: 'statements/:yearMonth', + SIGN_IN_MODAL: 'sign-in-modal', -export default { BANK_ACCOUNT: 'bank-account', BANK_ACCOUNT_NEW: 'bank-account/new', - BANK_ACCOUNT_WITH_STEP_TO_OPEN: 'bank-account/:stepToOpen?', BANK_ACCOUNT_PERSONAL: 'bank-account/personal', - getBankAccountRoute: (stepToOpen = '', policyID = '', backTo = ''): string => { - const backToParam = backTo ? `&backTo=${encodeURIComponent(backTo)}` : ''; - return `bank-account/${stepToOpen}?policyID=${policyID}${backToParam}`; + BANK_ACCOUNT_WITH_STEP_TO_OPEN: { + route: 'bank-account/:stepToOpen?', + getRoute: (stepToOpen = '', policyID = '', backTo = ''): string => { + const backToParam = backTo ? `&backTo=${encodeURIComponent(backTo)}` : ''; + return `bank-account/${stepToOpen}?policyID=${policyID}${backToParam}`; + }, }, - HOME: '', + SETTINGS: 'settings', SETTINGS_PROFILE: 'settings/profile', SETTINGS_SHARE_CODE: 'settings/shareCode', @@ -48,189 +63,112 @@ export default { SETTINGS_ABOUT: 'settings/about', SETTINGS_APP_DOWNLOAD_LINKS: 'settings/about/app-download-links', SETTINGS_WALLET: 'settings/wallet', - SETTINGS_ADD_PAYPAL_ME: 'settings/wallet/add-paypal-me', + SETTINGS_WALLET_DOMAINCARDS: { + route: '/settings/wallet/card/:domain', + getRoute: (domain: string) => `/settings/wallet/card/${domain}`, + }, SETTINGS_ADD_DEBIT_CARD: 'settings/wallet/add-debit-card', SETTINGS_ADD_BANK_ACCOUNT: 'settings/wallet/add-bank-account', SETTINGS_ENABLE_PAYMENTS: 'settings/wallet/enable-payments', - getSettingsAddLoginRoute: (type: string) => `settings/addlogin/${type}`, SETTINGS_WALLET_TRANSFER_BALANCE: 'settings/wallet/transfer-balance', SETTINGS_WALLET_CHOOSE_TRANSFER_ACCOUNT: 'settings/wallet/choose-transfer-account', - SETTINGS_PERSONAL_DETAILS, - SETTINGS_PERSONAL_DETAILS_LEGAL_NAME: `${SETTINGS_PERSONAL_DETAILS}/legal-name`, - SETTINGS_PERSONAL_DETAILS_DATE_OF_BIRTH: `${SETTINGS_PERSONAL_DETAILS}/date-of-birth`, - SETTINGS_PERSONAL_DETAILS_ADDRESS: `${SETTINGS_PERSONAL_DETAILS}/address`, - SETTINGS_CONTACT_METHODS, - SETTINGS_CONTACT_METHOD_DETAILS: `${SETTINGS_CONTACT_METHODS}/:contactMethod/details`, - getEditContactMethodRoute: (contactMethod: string) => `${SETTINGS_CONTACT_METHODS}/${encodeURIComponent(contactMethod)}/details`, - SETTINGS_NEW_CONTACT_METHOD: `${SETTINGS_CONTACT_METHODS}/new`, + SETTINGS_PERSONAL_DETAILS: 'settings/profile/personal-details', + SETTINGS_PERSONAL_DETAILS_LEGAL_NAME: 'settings/profile/personal-details/legal-name', + SETTINGS_PERSONAL_DETAILS_DATE_OF_BIRTH: 'settings/profile/personal-details/date-of-birth', + SETTINGS_PERSONAL_DETAILS_ADDRESS: 'settings/profile/personal-details/address', + SETTINGS_CONTACT_METHODS: 'settings/profile/contact-methods', + SETTINGS_CONTACT_METHOD_DETAILS: { + route: 'settings/profile/contact-methods/:contactMethod/details', + getRoute: (contactMethod: string) => `settings/profile/contact-methods/${encodeURIComponent(contactMethod)}/details`, + }, + SETTINGS_NEW_CONTACT_METHOD: 'settings/profile/contact-methods/new', SETTINGS_2FA: 'settings/security/two-factor-auth', - SETTINGS_STATUS, - SETTINGS_STATUS_SET, + SETTINGS_STATUS: 'settings/profile/status', + SETTINGS_STATUS_SET: 'settings/profile/status/set', + NEW: 'new', NEW_CHAT: 'new/chat', NEW_ROOM: 'new/room', - NEW_TASK, - REPORT, - REPORT_WITH_ID: 'r/:reportID?/:reportActionID?', - EDIT_REQUEST: 'r/:threadReportID/edit/:field', - getEditRequestRoute: (threadReportID: string, field: ValueOf) => `r/${threadReportID}/edit/${field}`, - EDIT_CURRENCY_REQUEST: 'r/:threadReportID/edit/currency', - getEditRequestCurrencyRoute: (threadReportID: string, currency: string, backTo: string) => `r/${threadReportID}/edit/currency?currency=${currency}&backTo=${backTo}`, - getReportRoute: (reportID: string) => `r/${reportID}`, - REPORT_WITH_ID_DETAILS_SHARE_CODE: 'r/:reportID/details/shareCode', - getReportShareCodeRoute: (reportID: string) => `r/${reportID}/details/shareCode`, - REPORT_ATTACHMENTS: 'r/:reportID/attachment', - getReportAttachmentRoute: (reportID: string, source: string) => `r/${reportID}/attachment?source=${encodeURI(source)}`, - - /** This is a utility route used to go to the user's concierge chat, or the sign-in page if the user's not authenticated */ - CONCIERGE: 'concierge', - IOU_REQUEST, - IOU_SEND, + REPORT: 'r', + REPORT_WITH_ID: {route: 'r/:reportID?/:reportActionID?', getRoute: (reportID: string) => `r/${reportID}`}, + EDIT_REQUEST: {route: 'r/:threadReportID/edit/:field', getRoute: (threadReportID: string, field: ValueOf) => `r/${threadReportID}/edit/${field}`}, + EDIT_CURRENCY_REQUEST: { + route: 'r/:threadReportID/edit/currency', + getRoute: (threadReportID: string, currency: string, backTo: string) => `r/${threadReportID}/edit/currency?currency=${currency}&backTo=${backTo}`, + }, + REPORT_WITH_ID_DETAILS_SHARE_CODE: {route: 'r/:reportID/details/shareCode', getRoute: (reportID: string) => `r/${reportID}/details/shareCode`}, + REPORT_ATTACHMENTS: {route: 'r/:reportID/attachment', getRoute: (reportID: string, source: string) => `r/${reportID}/attachment?source=${encodeURI(source)}`}, + REPORT_PARTICIPANTS: {route: 'r/:reportID/participants', getRoute: (reportID: string) => `r/${reportID}/participants`}, + REPORT_WITH_ID_DETAILS: {route: 'r/:reportID/details', getRoute: (reportID: string) => `r/${reportID}/details`}, + REPORT_SETTINGS: {route: 'r/:reportID/settings', getRoute: (reportID: string) => `r/${reportID}/settings`}, + REPORT_SETTINGS_ROOM_NAME: {route: 'r/:reportID/settings/room-name', getRoute: (reportID: string) => `r/${reportID}/settings/room-name`}, + REPORT_SETTINGS_NOTIFICATION_PREFERENCES: {route: 'r/:reportID/settings/notification-preferences', getRoute: (reportID: string) => `r/${reportID}/settings/notification-preferences`}, + REPORT_SETTINGS_WRITE_CAPABILITY: {route: 'r/:reportID/settings/who-can-post', getRoute: (reportID: string) => `r/${reportID}/settings/who-can-post`}, + REPORT_WELCOME_MESSAGE: {route: 'r/:reportID/welcomeMessage', getRoute: (reportID: string) => `r/${reportID}/welcomeMessage`}, + SPLIT_BILL_DETAILS: {route: 'r/:reportID/split/:reportActionID', getRoute: (reportID: string, reportActionID: string) => `r/${reportID}/split/${reportActionID}`}, + TASK_TITLE: {route: 'r/:reportID/title', getRoute: (reportID: string) => `r/${reportID}/title`}, + TASK_DESCRIPTION: {route: 'r/:reportID/description', getRoute: (reportID: string) => `r/${reportID}/description`}, + TASK_ASSIGNEE: {route: 'r/:reportID/assignee', getRoute: (reportID: string) => `r/${reportID}/assignee`}, + PRIVATE_NOTES_VIEW: {route: 'r/:reportID/notes/:accountID', getRoute: (reportID: string, accountID: string | number) => `r/${reportID}/notes/${accountID}`}, + PRIVATE_NOTES_LIST: {route: 'r/:reportID/notes', getRoute: (reportID: string) => `r/${reportID}/notes`}, + PRIVATE_NOTES_EDIT: {route: 'r/:reportID/notes/:accountID/edit', getRoute: (reportID: string, accountID: string | number) => `r/${reportID}/notes/${accountID}/edit`}, // To see the available iouType, please refer to CONST.IOU.MONEY_REQUEST_TYPE - MONEY_REQUEST: ':iouType/new/:reportID?', - MONEY_REQUEST_AMOUNT: ':iouType/new/amount/:reportID?', - MONEY_REQUEST_PARTICIPANTS: ':iouType/new/participants/:reportID?', - MONEY_REQUEST_CONFIRMATION: ':iouType/new/confirmation/:reportID?', - MONEY_REQUEST_DATE: ':iouType/new/date/:reportID?', - MONEY_REQUEST_CURRENCY: ':iouType/new/currency/:reportID?', - MONEY_REQUEST_DESCRIPTION: ':iouType/new/description/:reportID?', - MONEY_REQUEST_CATEGORY: ':iouType/new/category/:reportID?', - MONEY_REQUEST_TAG: ':iouType/new/tag/:reportID?', - MONEY_REQUEST_MERCHANT: ':iouType/new/merchant/:reportID?', + MONEY_REQUEST: {route: ':iouType/new/:reportID?', getRoute: (iouType: string, reportID = '') => `${iouType}/new/${reportID}`}, + MONEY_REQUEST_AMOUNT: {route: ':iouType/new/amount/:reportID?', getRoute: (iouType: string, reportID = '') => `${iouType}/new/amount/${reportID}`}, + MONEY_REQUEST_PARTICIPANTS: {route: ':iouType/new/participants/:reportID?', getRoute: (iouType: string, reportID = '') => `${iouType}/new/participants/${reportID}`}, + MONEY_REQUEST_CONFIRMATION: {route: ':iouType/new/confirmation/:reportID?', getRoute: (iouType: string, reportID = '') => `${iouType}/new/confirmation/${reportID}`}, + MONEY_REQUEST_DATE: {route: ':iouType/new/date/:reportID?', getRoute: (iouType: string, reportID = '') => `${iouType}/new/date/${reportID}`}, + MONEY_REQUEST_CURRENCY: { + route: ':iouType/new/currency/:reportID?', + getRoute: (iouType: string, reportID: string, currency: string, backTo: string) => `${iouType}/new/currency/${reportID}?currency=${currency}&backTo=${backTo}`, + }, + MONEY_REQUEST_DESCRIPTION: {route: ':iouType/new/description/:reportID?', getRoute: (iouType: string, reportID = '') => `${iouType}/new/description/${reportID}`}, + MONEY_REQUEST_CATEGORY: {route: ':iouType/new/category/:reportID?', getRoute: (iouType: string, reportID = '') => `${iouType}/new/category/${reportID}`}, + MONEY_REQUEST_TAG: {route: ':iouType/new/tag/:reportID?', getRoute: (iouType: string, reportID = '') => `${iouType}/new/tag/${reportID}`}, + MONEY_REQUEST_MERCHANT: {route: ':iouType/new/merchant/:reportID?', getRoute: (iouType: string, reportID = '') => `${iouType}/new/merchant/${reportID}`}, + MONEY_REQUEST_WAYPOINT: {route: ':iouType/new/waypoint/:waypointIndex', getRoute: (iouType: string, waypointIndex: number) => `${iouType}/new/waypoint/${waypointIndex}`}, + MONEY_REQUEST_RECEIPT: {route: ':iouType/new/receipt/:reportID?', getRoute: (iouType: string, reportID = '') => `${iouType}/new/receipt/${reportID}`}, + MONEY_REQUEST_ADDRESS: {route: ':iouType/new/address/:reportID?', getRoute: (iouType: string, reportID = '') => `${iouType}/new/address/${reportID}`}, + MONEY_REQUEST_DISTANCE_TAB: {route: ':iouType/new/:reportID?/distance', getRoute: (iouType: string, reportID = '') => `${iouType}/new/${reportID}/distance`}, MONEY_REQUEST_MANUAL_TAB: ':iouType/new/:reportID?/manual', MONEY_REQUEST_SCAN_TAB: ':iouType/new/:reportID?/scan', - MONEY_REQUEST_DISTANCE_TAB: ':iouType/new/:reportID?/distance', - MONEY_REQUEST_WAYPOINT: ':iouType/new/waypoint/:waypointIndex', - MONEY_REQUEST_ADDRESS: ':iouType/new/address/:reportID?', - IOU_SEND_ADD_BANK_ACCOUNT: `${IOU_SEND}/add-bank-account`, - IOU_SEND_ADD_DEBIT_CARD: `${IOU_SEND}/add-debit-card`, - IOU_SEND_ENABLE_PAYMENTS: `${IOU_SEND}/enable-payments`, - getMoneyRequestRoute: (iouType: string, reportID = '') => `${iouType}/new/${reportID}`, - getMoneyRequestAmountRoute: (iouType: string, reportID = '') => `${iouType}/new/amount/${reportID}`, - getMoneyRequestParticipantsRoute: (iouType: string, reportID = '') => `${iouType}/new/participants/${reportID}`, - getMoneyRequestConfirmationRoute: (iouType: string, reportID = '') => `${iouType}/new/confirmation/${reportID}`, - getMoneyRequestCreatedRoute: (iouType: string, reportID = '') => `${iouType}/new/date/${reportID}`, - getMoneyRequestCurrencyRoute: (iouType: string, reportID: string, currency: string, backTo: string) => `${iouType}/new/currency/${reportID}?currency=${currency}&backTo=${backTo}`, - getMoneyRequestDescriptionRoute: (iouType: string, reportID = '') => `${iouType}/new/description/${reportID}`, - getMoneyRequestCategoryRoute: (iouType: string, reportID = '') => `${iouType}/new/category/${reportID}`, - getMoneyRequestMerchantRoute: (iouType: string, reportID = '') => `${iouType}/new/merchant/${reportID}`, - getMoneyRequestDistanceTabRoute: (iouType: string, reportID = '') => `${iouType}/new/${reportID}/distance`, - getMoneyRequestWaypointRoute: (iouType: string, waypointIndex: number) => `${iouType}/new/waypoint/${waypointIndex}`, - getMoneyRequestAddressRoute: (iouType: string, reportID = '') => `${iouType}/new/address/${reportID}`, - getMoneyRequestTagRoute: (iouType: string, reportID = '') => `${iouType}/new/tag/${reportID}`, - SPLIT_BILL_DETAILS: `r/:reportID/split/:reportActionID`, - getSplitBillDetailsRoute: (reportID: string, reportActionID: string) => `r/${reportID}/split/${reportActionID}`, - getNewTaskRoute: (reportID: string) => `${NEW_TASK}/${reportID}`, - NEW_TASK_WITH_REPORT_ID: `${NEW_TASK}/:reportID?`, - TASK_TITLE: 'r/:reportID/title', - TASK_DESCRIPTION: 'r/:reportID/description', - TASK_ASSIGNEE: 'r/:reportID/assignee', - getTaskReportTitleRoute: (reportID: string) => `r/${reportID}/title`, - getTaskReportDescriptionRoute: (reportID: string) => `r/${reportID}/description`, - getTaskReportAssigneeRoute: (reportID: string) => `r/${reportID}/assignee`, - NEW_TASK_ASSIGNEE: `${NEW_TASK}/assignee`, - NEW_TASK_SHARE_DESTINATION: `${NEW_TASK}/share-destination`, - NEW_TASK_DETAILS: `${NEW_TASK}/details`, - NEW_TASK_TITLE: `${NEW_TASK}/title`, - NEW_TASK_DESCRIPTION: `${NEW_TASK}/description`, - FLAG_COMMENT: `flag/:reportID/:reportActionID`, - getFlagCommentRoute: (reportID: string, reportActionID: string) => `flag/${reportID}/${reportActionID}`, - SEARCH: 'search', + + IOU_REQUEST: 'request/new', + IOU_SEND: 'send/new', + IOU_SEND_ADD_BANK_ACCOUNT: 'send/new/add-bank-account', + IOU_SEND_ADD_DEBIT_CARD: 'send/new/add-debit-card', + IOU_SEND_ENABLE_PAYMENTS: 'send/new/enable-payments', + + NEW_TASK: 'new/task', + NEW_TASK_WITH_REPORT_ID: 'new/task/:reportID?', + NEW_TASK_ASSIGNEE: 'new/task/assignee', + NEW_TASK_SHARE_DESTINATION: 'new/task/share-destination', + NEW_TASK_DETAILS: 'new/task/details', + NEW_TASK_TITLE: 'new/task/title', + NEW_TASK_DESCRIPTION: 'new/task/description', + TEACHERS_UNITE: 'teachersunite', I_KNOW_A_TEACHER: 'teachersunite/i-know-a-teacher', - INTRO_SCHOOL_PRINCIPAL: 'teachersunite/intro-school-principal', I_AM_A_TEACHER: 'teachersunite/i-am-a-teacher', - DETAILS: 'details', - getDetailsRoute: (login: string) => `details?login=${encodeURIComponent(login)}`, - PROFILE: 'a/:accountID', - getProfileRoute: (accountID: string | number, backTo = '') => { - const backToParam = backTo ? `?backTo=${encodeURIComponent(backTo)}` : ''; - return `a/${accountID}${backToParam}`; - }, - REPORT_PARTICIPANTS: 'r/:reportID/participants', - getReportParticipantsRoute: (reportID: string) => `r/${reportID}/participants`, - REPORT_WITH_ID_DETAILS: 'r/:reportID/details', - getReportDetailsRoute: (reportID: string) => `r/${reportID}/details`, - REPORT_SETTINGS: 'r/:reportID/settings', - getReportSettingsRoute: (reportID: string) => `r/${reportID}/settings`, - REPORT_SETTINGS_ROOM_NAME: 'r/:reportID/settings/room-name', - getReportSettingsRoomNameRoute: (reportID: string) => `r/${reportID}/settings/room-name`, - REPORT_SETTINGS_NOTIFICATION_PREFERENCES: 'r/:reportID/settings/notification-preferences', - getReportSettingsNotificationPreferencesRoute: (reportID: string) => `r/${reportID}/settings/notification-preferences`, - REPORT_WELCOME_MESSAGE: 'r/:reportID/welcomeMessage', - getReportWelcomeMessageRoute: (reportID: string) => `r/${reportID}/welcomeMessage`, - REPORT_SETTINGS_WRITE_CAPABILITY: 'r/:reportID/settings/who-can-post', - getReportSettingsWriteCapabilityRoute: (reportID: string) => `r/${reportID}/settings/who-can-post`, - TRANSITION_BETWEEN_APPS: 'transition', - VALIDATE_LOGIN: 'v/:accountID/:validateCode', - GET_ASSISTANCE: 'get-assistance/:taskID', - getGetAssistanceRoute: (taskID: string) => `get-assistance/${taskID}`, - UNLINK_LOGIN: 'u/:accountID/:validateCode', - - APPLE_SIGN_IN: 'sign-in-with-apple', - GOOGLE_SIGN_IN: 'sign-in-with-google', - DESKTOP_SIGN_IN_REDIRECT: 'desktop-signin-redirect', - - // Routes related to private notes added to the report - PRIVATE_NOTES_VIEW: 'r/:reportID/notes/:accountID', - getPrivateNotesViewRoute: (reportID: string, accountID: string | number) => `r/${reportID}/notes/${accountID}`, - PRIVATE_NOTES_LIST: 'r/:reportID/notes', - getPrivateNotesListRoute: (reportID: string) => `r/${reportID}/notes`, - PRIVATE_NOTES_EDIT: 'r/:reportID/notes/:accountID/edit', - getPrivateNotesEditRoute: (reportID: string, accountID: string | number) => `r/${reportID}/notes/${accountID}/edit`, + INTRO_SCHOOL_PRINCIPAL: 'teachersunite/intro-school-principal', - // This is a special validation URL that will take the user to /workspace/new after validation. This is used - // when linking users from e.com in order to share a session in this app. - ENABLE_PAYMENTS: 'enable-payments', - WALLET_STATEMENT_WITH_DATE: 'statements/:yearMonth', - getWalletStatementWithDateRoute: (yearMonth: string) => `statements/${yearMonth}`, WORKSPACE_NEW: 'workspace/new', - WORKSPACE_INITIAL: 'workspace/:policyID', - WORKSPACE_INVITE: 'workspace/:policyID/invite', - WORKSPACE_INVITE_MESSAGE: 'workspace/:policyID/invite-message', - WORKSPACE_SETTINGS: 'workspace/:policyID/settings', - WORKSPACE_CARD: 'workspace/:policyID/card', - WORKSPACE_REIMBURSE: 'workspace/:policyID/reimburse', - WORKSPACE_RATE_AND_UNIT: 'workspace/:policyID/rateandunit', - WORKSPACE_BILLS: 'workspace/:policyID/bills', - WORKSPACE_INVOICES: 'workspace/:policyID/invoices', - WORKSPACE_TRAVEL: 'workspace/:policyID/travel', - WORKSPACE_MEMBERS: 'workspace/:policyID/members', WORKSPACE_NEW_ROOM: 'workspace/new-room', - getWorkspaceInitialRoute: (policyID: string) => `workspace/${policyID}`, - getWorkspaceInviteRoute: (policyID: string) => `workspace/${policyID}/invite`, - getWorkspaceInviteMessageRoute: (policyID: string) => `workspace/${policyID}/invite-message`, - getWorkspaceSettingsRoute: (policyID: string) => `workspace/${policyID}/settings`, - getWorkspaceCardRoute: (policyID: string) => `workspace/${policyID}/card`, - getWorkspaceReimburseRoute: (policyID: string) => `workspace/${policyID}/reimburse`, - getWorkspaceRateAndUnitRoute: (policyID: string) => `workspace/${policyID}/rateandunit`, - getWorkspaceBillsRoute: (policyID: string) => `workspace/${policyID}/bills`, - getWorkspaceInvoicesRoute: (policyID: string) => `workspace/${policyID}/invoices`, - getWorkspaceTravelRoute: (policyID: string) => `workspace/${policyID}/travel`, - getWorkspaceMembersRoute: (policyID: string) => `workspace/${policyID}/members`, + WORKSPACE_INITIAL: {route: 'workspace/:policyID', getRoute: (policyID: string) => `workspace/${policyID}`}, + WORKSPACE_INVITE: {route: 'workspace/:policyID/invite', getRoute: (policyID: string) => `workspace/${policyID}/invite`}, + WORKSPACE_INVITE_MESSAGE: {route: 'workspace/:policyID/invite-message', getRoute: (policyID: string) => `workspace/${policyID}/invite-message`}, + WORKSPACE_SETTINGS: {route: 'workspace/:policyID/settings', getRoute: (policyID: string) => `workspace/${policyID}/settings`}, + WORKSPACE_CARD: {route: 'workspace/:policyID/card', getRoute: (policyID: string) => `workspace/${policyID}/card`}, + WORKSPACE_REIMBURSE: {route: 'workspace/:policyID/reimburse', getRoute: (policyID: string) => `workspace/${policyID}/reimburse`}, + WORKSPACE_RATE_AND_UNIT: {route: 'workspace/:policyID/rateandunit', getRoute: (policyID: string) => `workspace/${policyID}/rateandunit`}, + WORKSPACE_BILLS: {route: 'workspace/:policyID/bills', getRoute: (policyID: string) => `workspace/${policyID}/bills`}, + WORKSPACE_INVOICES: {route: 'workspace/:policyID/invoices', getRoute: (policyID: string) => `workspace/${policyID}/invoices`}, + WORKSPACE_TRAVEL: {route: 'workspace/:policyID/travel', getRoute: (policyID: string) => `workspace/${policyID}/travel`}, + WORKSPACE_MEMBERS: {route: 'workspace/:policyID/members', getRoute: (policyID: string) => `workspace/${policyID}/members`}, // These are some on-off routes that will be removed once they're no longer needed (see GH issues for details) SAASTR: 'saastr', SBE: 'sbe', - - parseReportRouteParams: (route: string): ParseReportRouteParams => { - let parsingRoute = route; - if (parsingRoute.at(0) === '/') { - // remove the first slash - parsingRoute = parsingRoute.slice(1); - } - - if (!parsingRoute.startsWith(Url.addTrailingForwardSlash(REPORT))) { - return {reportID: '', isSubReportPageRoute: false}; - } - - const pathSegments = parsingRoute.split('/'); - return { - reportID: pathSegments[1], - isSubReportPageRoute: pathSegments.length > 2, - }; - }, - SIGN_IN_MODAL: 'sign-in-modal', } as const; diff --git a/src/SCREENS.ts b/src/SCREENS.ts index 47935e117e99..eb125a43c239 100644 --- a/src/SCREENS.ts +++ b/src/SCREENS.ts @@ -12,8 +12,14 @@ export default { VALIDATE_LOGIN: 'ValidateLogin', CONCIERGE: 'Concierge', SETTINGS: { + ROOT: 'Settings_Root', PREFERENCES: 'Settings_Preferences', WORKSPACES: 'Settings_Workspaces', + SECURITY: 'Settings_Security', + STATUS: 'Settings_Status', + }, + SAVE_THE_WORLD: { + ROOT: 'SaveTheWorld_Root', }, SIGN_IN_WITH_APPLE_DESKTOP: 'AppleSignInDesktop', SIGN_IN_WITH_GOOGLE_DESKTOP: 'GoogleSignInDesktop', diff --git a/src/components/AddPaymentMethodMenu.js b/src/components/AddPaymentMethodMenu.js index 7f1544a758f4..399247a35676 100644 --- a/src/components/AddPaymentMethodMenu.js +++ b/src/components/AddPaymentMethodMenu.js @@ -10,7 +10,6 @@ import withWindowDimensions from './withWindowDimensions'; import Permissions from '../libs/Permissions'; import PopoverMenu from './PopoverMenu'; import refPropTypes from './refPropTypes'; -import paypalMeDataPropTypes from './paypalMeDataPropTypes'; const propTypes = { /** Should the component be visible? */ @@ -25,12 +24,6 @@ const propTypes = { vertical: PropTypes.number, }), - /** Account details for PayPal.Me */ - payPalMeData: paypalMeDataPropTypes, - - /** Should we show the Paypal option */ - shouldShowPaypal: PropTypes.bool, - /** List of betas available to current user */ betas: PropTypes.arrayOf(PropTypes.string), @@ -42,8 +35,6 @@ const propTypes = { const defaultProps = { anchorPosition: {}, - payPalMeData: {}, - shouldShowPaypal: true, betas: [], anchorRef: () => {}, }; @@ -73,15 +64,6 @@ function AddPaymentMethodMenu(props) { }, ] : []), - ...(props.shouldShowPaypal && !props.payPalMeData.description - ? [ - { - text: props.translate('common.payPalMe'), - icon: Expensicons.PayPal, - onSelected: () => props.onItemSelected(CONST.PAYMENT_METHODS.PAYPAL), - }, - ] - : []), ]} withoutOverlay /> @@ -96,9 +78,6 @@ export default compose( withWindowDimensions, withLocalize, withOnyx({ - payPalMeData: { - key: ONYXKEYS.PAYPAL, - }, betas: { key: ONYXKEYS.BETAS, }, diff --git a/src/components/AddPlaidBankAccount.js b/src/components/AddPlaidBankAccount.js index e2843ba7fae8..dbe7e46ff6aa 100644 --- a/src/components/AddPlaidBankAccount.js +++ b/src/components/AddPlaidBankAccount.js @@ -1,7 +1,6 @@ import _ from 'underscore'; -import React, {useEffect, useRef, useCallback, useMemo} from 'react'; +import React, {useEffect, useRef, useCallback} from 'react'; import {ActivityIndicator, View} from 'react-native'; -import {useIsFocused} from '@react-navigation/native'; import PropTypes from 'prop-types'; import {withOnyx} from 'react-native-onyx'; import lodashGet from 'lodash/get'; @@ -39,9 +38,6 @@ const propTypes = { /** Fired when the user exits the Plaid flow */ onExitPlaid: PropTypes.func, - /** Fired when the screen is blurred */ - onBlurPlaid: PropTypes.func, - /** Fired when the user selects an account */ onSelect: PropTypes.func, @@ -65,7 +61,6 @@ const defaultProps = { selectedPlaidAccountID: '', plaidLinkToken: '', onExitPlaid: () => {}, - onBlurPlaid: () => {}, onSelect: () => {}, text: '', receivedRedirectURI: null, @@ -80,7 +75,6 @@ function AddPlaidBankAccount({ selectedPlaidAccountID, plaidLinkToken, onExitPlaid, - onBlurPlaid, onSelect, text, receivedRedirectURI, @@ -94,7 +88,6 @@ function AddPlaidBankAccount({ const {translate} = useLocalize(); const {isOffline} = useNetwork(); - const isFocused = useIsFocused(); /** * @returns {String} @@ -109,11 +102,6 @@ function AddPlaidBankAccount({ } }; - /** - * @returns {Array} - */ - const plaidBankAccounts = useMemo(() => lodashGet(plaidData, 'bankAccounts') || [], [plaidData]); - /** * @returns {Boolean} * I'm using useCallback so the useEffect which uses this function doesn't run on every render. @@ -163,13 +151,6 @@ function AddPlaidBankAccount({ // eslint-disable-next-line react-hooks/exhaustive-deps }, []); - useEffect(() => { - if (isFocused || plaidBankAccounts.length) { - return; - } - onBlurPlaid(); - }, [isFocused, onBlurPlaid, plaidBankAccounts.length]); - useEffect(() => { // If we are coming back from offline and we haven't authenticated with Plaid yet, we need to re-run our call to kick off Plaid // previousNetworkState.current also makes sure that this doesn't run on the first render. @@ -179,6 +160,7 @@ function AddPlaidBankAccount({ previousNetworkState.current = isOffline; }, [allowDebit, bankAccountID, isAuthenticatedWithPlaid, isOffline]); + const plaidBankAccounts = lodashGet(plaidData, 'bankAccounts') || []; const token = getPlaidLinkToken(); const options = _.map(plaidBankAccounts, (account) => ({ value: account.plaidAccountID, diff --git a/src/components/AddressSearch/index.js b/src/components/AddressSearch/index.js index 1697dddba805..1b4200572664 100644 --- a/src/components/AddressSearch/index.js +++ b/src/components/AddressSearch/index.js @@ -34,7 +34,7 @@ const propTypes = { onBlur: PropTypes.func, /** Error text to display */ - errorText: PropTypes.string, + errorText: PropTypes.oneOfType([PropTypes.string, PropTypes.arrayOf(PropTypes.oneOfType([PropTypes.string, PropTypes.object]))]), /** Hint text to display */ hint: PropTypes.string, @@ -300,7 +300,7 @@ function AddressSearch(props) { query={query} requestUrl={{ useOnPlatform: 'all', - url: ApiUtils.getCommandURL({command: 'Proxy_GooglePlaces&proxyUrl='}), + url: props.network.isOffline ? null : ApiUtils.getCommandURL({command: 'Proxy_GooglePlaces&proxyUrl='}), }} textInputProps={{ InputComp: TextInput, diff --git a/src/components/AttachmentModal.js b/src/components/AttachmentModal.js index bbb0662132d2..c0fe0e2d26f8 100755 --- a/src/components/AttachmentModal.js +++ b/src/components/AttachmentModal.js @@ -1,4 +1,4 @@ -import React, {useState, useCallback} from 'react'; +import React, {useState, useCallback, useRef} from 'react'; import PropTypes from 'prop-types'; import {View, Animated, Keyboard} from 'react-native'; import Str from 'expensify-common/lib/str'; @@ -25,6 +25,10 @@ import HeaderGap from './HeaderGap'; import SafeAreaConsumer from './SafeAreaConsumer'; import addEncryptedAuthTokenToURL from '../libs/addEncryptedAuthTokenToURL'; import reportPropTypes from '../pages/reportPropTypes'; +import * as Expensicons from './Icon/Expensicons'; +import useWindowDimensions from '../hooks/useWindowDimensions'; +import Navigation from '../libs/Navigation/Navigation'; +import ROUTES from '../ROUTES'; import useNativeDriver from '../libs/useNativeDriver'; /** @@ -94,6 +98,7 @@ const defaultProps = { }; function AttachmentModal(props) { + const onModalHideCallbackRef = useRef(null); const [isModalOpen, setIsModalOpen] = useState(props.defaultOpen); const [shouldLoadAttachment, setShouldLoadAttachment] = useState(false); const [isAttachmentInvalid, setIsAttachmentInvalid] = useState(false); @@ -106,6 +111,8 @@ function AttachmentModal(props) { const [isConfirmButtonDisabled, setIsConfirmButtonDisabled] = useState(false); const [confirmButtonFadeAnimation] = useState(new Animated.Value(1)); const [shouldShowDownloadButton, setShouldShowDownloadButton] = React.useState(true); + const {windowWidth} = useWindowDimensions(); + const [file, setFile] = useState( props.originalFileName ? { @@ -331,6 +338,10 @@ function AttachmentModal(props) { }} onModalHide={(e) => { props.onModalHide(e); + if (onModalHideCallbackRef.current) { + onModalHideCallbackRef.current(); + } + setShouldLoadAttachment(false); }} propagateSwipe @@ -339,12 +350,30 @@ function AttachmentModal(props) { downloadAttachment(source)} shouldShowCloseButton={!props.isSmallScreenWidth} shouldShowBackButton={props.isSmallScreenWidth} onBackButtonPress={closeModal} onCloseButtonPress={closeModal} + shouldShowThreeDotsButton={isAttachmentReceipt} + threeDotsAnchorPosition={styles.threeDotsPopoverOffsetAttachmentModal(windowWidth)} + threeDotsMenuItems={[ + { + icon: Expensicons.Camera, + text: props.translate('common.replace'), + onSelected: () => { + onModalHideCallbackRef.current = () => Navigation.navigate(ROUTES.EDIT_REQUEST.getRoute(props.report.reportID, CONST.EDIT_REQUEST_FIELD.RECEIPT)); + closeModal(); + }, + }, + { + icon: Expensicons.Download, + text: props.translate('common.download'), + onSelected: () => downloadAttachment(source), + }, + ]} + shouldOverlay /> {!_.isEmpty(props.report) ? ( @@ -366,6 +395,7 @@ function AttachmentModal(props) { file={file} onToggleKeyboard={updateConfirmButtonVisibility} isWorkspaceAvatar={props.isWorkspaceAvatar} + fallbackSource={props.fallbackSource} /> ) )} diff --git a/src/components/Attachments/AttachmentCarousel/AttachmentCarouselCellRenderer.js b/src/components/Attachments/AttachmentCarousel/AttachmentCarouselCellRenderer.js new file mode 100644 index 000000000000..2c698d5c8a61 --- /dev/null +++ b/src/components/Attachments/AttachmentCarousel/AttachmentCarouselCellRenderer.js @@ -0,0 +1,34 @@ +import React from 'react'; +import PropTypes from 'prop-types'; +import {View, PixelRatio} from 'react-native'; +import useWindowDimensions from '../../../hooks/useWindowDimensions'; +import styles from '../../../styles/styles'; + +const propTypes = { + /** Cell Container styles */ + style: PropTypes.oneOfType([PropTypes.arrayOf(PropTypes.object), PropTypes.object]), +}; + +const defaultProps = { + style: [], +}; + +function AttachmentCarouselCellRenderer(props) { + const {windowWidth, isSmallScreenWidth} = useWindowDimensions(); + const modalStyles = styles.centeredModalStyles(isSmallScreenWidth, true); + const style = [props.style, styles.h100, {width: PixelRatio.roundToNearestPixel(windowWidth - (modalStyles.marginHorizontal + modalStyles.borderWidth) * 2)}]; + + return ( + + ); +} + +AttachmentCarouselCellRenderer.propTypes = propTypes; +AttachmentCarouselCellRenderer.defaultProps = defaultProps; +AttachmentCarouselCellRenderer.displayName = 'AttachmentCarouselCellRenderer'; + +export default React.memo(AttachmentCarouselCellRenderer); diff --git a/src/components/Attachments/AttachmentCarousel/Pager/AttachmentCarouselPage.js b/src/components/Attachments/AttachmentCarousel/Pager/AttachmentCarouselPage.js index b1a844e4172d..f7da8cfce894 100644 --- a/src/components/Attachments/AttachmentCarousel/Pager/AttachmentCarouselPage.js +++ b/src/components/Attachments/AttachmentCarousel/Pager/AttachmentCarouselPage.js @@ -1,5 +1,5 @@ /* eslint-disable es/no-optional-chaining */ -import React, {useContext, useEffect, useState} from 'react'; +import React, {useContext, useEffect, useRef, useState} from 'react'; import {ActivityIndicator, PixelRatio, StyleSheet, View} from 'react-native'; import PropTypes from 'prop-types'; import Image from '../../../Image'; @@ -41,18 +41,27 @@ function AttachmentCarouselPage({source, isAuthTokenRequired, isActive: initialI // to prevent the image transformer from flashing while still rendering // Instead, we show the fallback image while the image transformer is loading the image useEffect(() => { - if (initialIsActive) setTimeout(() => setIsActive(true), 1); - else setIsActive(false); + if (initialIsActive) { + setTimeout(() => setIsActive(true), 1); + } else { + setIsActive(false); + } }, [initialIsActive]); const [initialActivePageLoad, setInitialActivePageLoad] = useState(isActive); - const [isImageLoading, setIsImageLoading] = useState(true); - const [showFallback, setShowFallback] = useState(isImageLoading); + const isImageLoaded = useRef(null); + const [isImageLoading, setIsImageLoading] = useState(false); + const [isFallbackLoading, setIsFallbackLoading] = useState(false); + const [showFallback, setShowFallback] = useState(true); // We delay hiding the fallback image while image transformer is still rendering useEffect(() => { - if (isImageLoading) setShowFallback(true); - else setTimeout(() => setShowFallback(false), 100); + if (isImageLoading || showFallback) { + setShowFallback(true); + } else { + setTimeout(() => setShowFallback(false), 100); + } + // eslint-disable-next-line react-hooks/exhaustive-deps }, [isImageLoading]); return ( @@ -73,8 +82,14 @@ function AttachmentCarouselPage({source, isAuthTokenRequired, isActive: initialI source={{uri: source}} style={dimensions == null ? undefined : {width: dimensions.imageWidth, height: dimensions.imageHeight}} isAuthTokenRequired={isAuthTokenRequired} - onLoadStart={() => setIsImageLoading(true)} - onLoadEnd={() => setIsImageLoading(false)} + onLoadStart={() => { + setIsImageLoading(true); + }} + onLoadEnd={() => { + setShowFallback(false); + setIsImageLoading(false); + isImageLoaded.current = true; + }} onLoad={(evt) => { const imageWidth = (evt.nativeEvent?.width || 0) / PixelRatio.get(); const imageHeight = (evt.nativeEvent?.height || 0) / PixelRatio.get(); @@ -100,8 +115,10 @@ function AttachmentCarouselPage({source, isAuthTokenRequired, isActive: initialI // On the initial render of the active page, the onLoadEnd event is never fired. // That's why we instead set isImageLoading to false in the onLoad event. if (initialActivePageLoad) { - setIsImageLoading(false); setInitialActivePageLoad(false); + setIsImageLoading(false); + setTimeout(() => setShowFallback(false), 100); + isImageLoaded.current = true; } }} /> @@ -110,12 +127,24 @@ function AttachmentCarouselPage({source, isAuthTokenRequired, isActive: initialI )} {/* Keep rendering the image without gestures as fallback while ImageTransformer is loading the image */} - {(!isActive || showFallback) && ( + {(showFallback || !isActive) && ( setIsImageLoading(true)} + onLoadStart={() => { + setIsImageLoading(true); + if (isImageLoaded.current) { + return; + } + setIsFallbackLoading(true); + }} + onLoadEnd={() => { + if (isImageLoaded.current) { + return; + } + setIsFallbackLoading(false); + }} onLoad={(evt) => { const imageWidth = evt.nativeEvent.width; const imageHeight = evt.nativeEvent.height; @@ -127,7 +156,9 @@ function AttachmentCarouselPage({source, isAuthTokenRequired, isActive: initialI const scaledImageHeight = imageHeight * minImageScale; // Don't update the dimensions if they are already set - if (dimensions?.scaledImageWidth === scaledImageWidth && dimensions?.scaledImageHeight === scaledImageHeight) return; + if (dimensions?.scaledImageWidth === scaledImageWidth && dimensions?.scaledImageHeight === scaledImageHeight) { + return; + } cachedDimensions.set(source, { ...dimensions, @@ -141,7 +172,7 @@ function AttachmentCarouselPage({source, isAuthTokenRequired, isActive: initialI )} {/* Show activity indicator while ImageTransfomer is still loading the image. */} - {isActive && isImageLoading && ( + {isActive && isFallbackLoading && !isImageLoaded.current && ( { - if (!success || !onTap) return; + if (!success || !onTap) { + return; + } runOnJS(onTap)(); }); @@ -432,7 +434,9 @@ function ImageTransformer({imageWidth, imageHeight, imageScaleX, imageScaleY, sc const pinchGesture = Gesture.Pinch() .onTouchesDown((evt, state) => { // we don't want to activate pinch gesture when we are scrolling pager - if (!isScrolling.value) return; + if (!isScrolling.value) { + return; + } state.fail(); }) diff --git a/src/components/Attachments/AttachmentCarousel/index.js b/src/components/Attachments/AttachmentCarousel/index.js index 574cb496d02f..00b603cdd7d9 100644 --- a/src/components/Attachments/AttachmentCarousel/index.js +++ b/src/components/Attachments/AttachmentCarousel/index.js @@ -3,6 +3,7 @@ import {View, FlatList, PixelRatio, Keyboard} from 'react-native'; import {withOnyx} from 'react-native-onyx'; import _ from 'underscore'; import styles from '../../../styles/styles'; +import AttachmentCarouselCellRenderer from './AttachmentCarouselCellRenderer'; import CarouselActions from './CarouselActions'; import withWindowDimensions from '../../withWindowDimensions'; import CarouselButtons from './CarouselButtons'; @@ -12,7 +13,6 @@ import ONYXKEYS from '../../../ONYXKEYS'; import withLocalize from '../../withLocalize'; import compose from '../../../libs/compose'; import useCarouselArrows from './useCarouselArrows'; -import useWindowDimensions from '../../../hooks/useWindowDimensions'; import CarouselItem from './CarouselItem'; import Navigation from '../../../libs/Navigation/Navigation'; import BlockingView from '../../BlockingViews/BlockingView'; @@ -30,7 +30,6 @@ const viewabilityConfig = { function AttachmentCarousel({report, reportActions, source, onNavigate, setDownloadButtonVisibility, translate}) { const scrollRef = useRef(null); - const {windowWidth, isSmallScreenWidth} = useWindowDimensions(); const canUseTouchScreen = DeviceCapabilities.canUseTouchScreen(); const [containerWidth, setContainerWidth] = useState(0); @@ -67,7 +66,9 @@ function AttachmentCarousel({report, reportActions, source, onNavigate, setDownl setDownloadButtonVisibility(initialPage !== -1); // Update the parent modal's state with the source and name from the mapped attachments - if (!_.isUndefined(attachmentsFromReport[initialPage])) onNavigate(attachmentsFromReport[initialPage]); + if (!_.isUndefined(attachmentsFromReport[initialPage])) { + onNavigate(attachmentsFromReport[initialPage]); + } } // eslint-disable-next-line react-hooks/exhaustive-deps }, [reportActions, compareImage]); @@ -130,29 +131,6 @@ function AttachmentCarousel({report, reportActions, source, onNavigate, setDownl [containerWidth], ); - /** - * Defines how a container for a single attachment should be rendered - * @param {Object} cellRendererProps - * @returns {JSX.Element} - */ - const renderCell = useCallback( - (cellProps) => { - // Use window width instead of layout width to address the issue in https://github.com/Expensify/App/issues/17760 - // considering horizontal margin and border width in centered modal - const modalStyles = styles.centeredModalStyles(isSmallScreenWidth, true); - const style = [cellProps.style, styles.h100, {width: PixelRatio.roundToNearestPixel(windowWidth - (modalStyles.marginHorizontal + modalStyles.borderWidth) * 2)}]; - - return ( - - ); - }, - [isSmallScreenWidth, windowWidth], - ); - /** * Defines how a single attachment should be rendered * @param {Object} item @@ -224,7 +202,7 @@ function AttachmentCarousel({report, reportActions, source, onNavigate, setDownl windowSize={5} maxToRenderPerBatch={3} data={attachments} - CellRendererComponent={renderCell} + CellRendererComponent={AttachmentCarouselCellRenderer} renderItem={renderItem} getItemLayout={getItemLayout} keyExtractor={(item) => item.source} diff --git a/src/components/Attachments/AttachmentCarousel/index.native.js b/src/components/Attachments/AttachmentCarousel/index.native.js index a7a2f35a2ccc..bd12020341be 100644 --- a/src/components/Attachments/AttachmentCarousel/index.native.js +++ b/src/components/Attachments/AttachmentCarousel/index.native.js @@ -56,7 +56,9 @@ function AttachmentCarousel({report, reportActions, source, onNavigate, onClose, setDownloadButtonVisibility(initialPage !== -1); // Update the parent modal's state with the source and name from the mapped attachments - if (!_.isUndefined(attachmentsFromReport[initialPage])) onNavigate(attachmentsFromReport[initialPage]); + if (!_.isUndefined(attachmentsFromReport[initialPage])) { + onNavigate(attachmentsFromReport[initialPage]); + } } // eslint-disable-next-line react-hooks/exhaustive-deps }, [reportActions, compareImage]); @@ -148,7 +150,9 @@ function AttachmentCarousel({report, reportActions, source, onNavigate, onClose, onPageSelected={({nativeEvent: {position: newPage}}) => updatePage(newPage)} onPinchGestureChange={(newIsPinchGestureRunning) => { setIsPinchGestureRunning(newIsPinchGestureRunning); - if (!newIsPinchGestureRunning && !shouldShowArrows) setShouldShowArrows(true); + if (!newIsPinchGestureRunning && !shouldShowArrows) { + setShouldShowArrows(true); + } }} onSwipeDown={onClose} containerWidth={containerDimensions.width} diff --git a/src/components/Attachments/AttachmentView/AttachmentViewImage/index.js b/src/components/Attachments/AttachmentView/AttachmentViewImage/index.js index 7de4417a4efc..48ac954ced7f 100755 --- a/src/components/Attachments/AttachmentView/AttachmentViewImage/index.js +++ b/src/components/Attachments/AttachmentView/AttachmentViewImage/index.js @@ -12,13 +12,14 @@ const propTypes = { ...withLocalizePropTypes, }; -function AttachmentViewImage({source, file, isAuthTokenRequired, loadComplete, onPress, isImage, onScaleChanged, translate}) { +function AttachmentViewImage({source, file, isAuthTokenRequired, loadComplete, onPress, isImage, onScaleChanged, translate, onError}) { const children = ( ); return onPress ? ( diff --git a/src/components/Attachments/AttachmentView/AttachmentViewPdf/index.native.js b/src/components/Attachments/AttachmentView/AttachmentViewPdf/index.native.js index 0767b2b68985..fdf151c4d5d0 100644 --- a/src/components/Attachments/AttachmentView/AttachmentViewPdf/index.native.js +++ b/src/components/Attachments/AttachmentView/AttachmentViewPdf/index.native.js @@ -25,7 +25,9 @@ function AttachmentViewPdf({file, encryptedSourceUrl, isFocused, isUsedInCarouse attachmentCarouselPagerContext.onPinchGestureChange(!shouldPagerScroll); - if (attachmentCarouselPagerContext.shouldPagerScroll.value === shouldPagerScroll) return; + if (attachmentCarouselPagerContext.shouldPagerScroll.value === shouldPagerScroll) { + return; + } attachmentCarouselPagerContext.shouldPagerScroll.value = shouldPagerScroll; } diff --git a/src/components/Attachments/AttachmentView/index.js b/src/components/Attachments/AttachmentView/index.js index 47353d915060..1fc579977c9d 100755 --- a/src/components/Attachments/AttachmentView/index.js +++ b/src/components/Attachments/AttachmentView/index.js @@ -17,6 +17,7 @@ import AttachmentViewPdf from './AttachmentViewPdf'; import addEncryptedAuthTokenToURL from '../../../libs/addEncryptedAuthTokenToURL'; import * as StyleUtils from '../../../styles/StyleUtils'; import {attachmentViewPropTypes, attachmentViewDefaultProps} from './propTypes'; +import useNetwork from '../../../hooks/useNetwork'; const propTypes = { ...attachmentViewPropTypes, @@ -62,9 +63,14 @@ function AttachmentView({ translate, isFocused, isWorkspaceAvatar, + fallbackSource, }) { const [loadComplete, setLoadComplete] = useState(false); + const [imageError, setImageError] = useState(false); + + useNetwork({onReconnect: () => setImageError(false)}); + // Handles case where source is a component (ex: SVG) if (_.isFunction(source)) { let iconFillColor = ''; @@ -113,7 +119,7 @@ function AttachmentView({ if (isImage || (file && Str.isImage(file.name))) { return ( { + setImageError(true); + }} /> ); } diff --git a/src/components/Avatar.js b/src/components/Avatar.js index b96e60dd56d1..4f0eb60eb2e0 100644 --- a/src/components/Avatar.js +++ b/src/components/Avatar.js @@ -1,4 +1,4 @@ -import React, {useState} from 'react'; +import React, {useEffect, useState} from 'react'; import {View} from 'react-native'; import PropTypes from 'prop-types'; import _ from 'underscore'; @@ -40,7 +40,7 @@ const propTypes = { /** A fallback avatar icon to display when there is an error on loading avatar from remote URL. * If the avatar is type === workspace, this fallback icon will be ignored and decided based on the name prop. */ - fallbackIcon: PropTypes.func, + fallbackIcon: PropTypes.oneOfType([PropTypes.func, PropTypes.string]), /** Denotes whether it is an avatar or a workspace avatar */ type: PropTypes.oneOf([CONST.ICON_TYPE_AVATAR, CONST.ICON_TYPE_WORKSPACE]), @@ -66,6 +66,10 @@ function Avatar(props) { useNetwork({onReconnect: () => setImageError(false)}); + useEffect(() => { + setImageError(false); + }, [props.source]); + if (!props.source) { return null; } @@ -81,14 +85,14 @@ function Avatar(props) { const iconStyle = props.imageStyles && props.imageStyles.length ? [StyleUtils.getAvatarStyle(props.size), styles.bgTransparent, ...props.imageStyles] : undefined; const iconFillColor = isWorkspace ? StyleUtils.getDefaultWorkspaceAvatarColor(props.name).fill : props.fill; - const fallbackAvatar = isWorkspace ? ReportUtils.getDefaultWorkspaceAvatar(props.name) : props.fallbackIcon; + const fallbackAvatar = isWorkspace ? ReportUtils.getDefaultWorkspaceAvatar(props.name) : props.fallbackIcon || Expensicons.FallbackAvatar; return ( - {_.isFunction(props.source) || imageError ? ( + {_.isFunction(props.source) || (imageError && _.isFunction(fallbackAvatar)) ? ( setImageError(true)} /> diff --git a/src/components/AvatarCropModal/AvatarCropModal.js b/src/components/AvatarCropModal/AvatarCropModal.js index baa958106f84..10e8a76f756d 100644 --- a/src/components/AvatarCropModal/AvatarCropModal.js +++ b/src/components/AvatarCropModal/AvatarCropModal.js @@ -366,6 +366,7 @@ function AvatarCropModal(props) { style={[styles.pb0]} includePaddingTop={false} includeSafeAreaPaddingBottom={false} + testID={AvatarCropModal.displayName} > {props.isSmallScreenWidth && } { if (ReportUtils.isExpenseReport(report)) { - Navigation.navigate(ROUTES.getProfileRoute(report.ownerAccountID)); + Navigation.navigate(ROUTES.PROFILE.getRoute(report.ownerAccountID)); return; } if (ReportUtils.isIOUReport(report)) { - Navigation.navigate(ROUTES.getReportParticipantsRoute(report.reportID)); + Navigation.navigate(ROUTES.REPORT_PARTICIPANTS.getRoute(report.reportID)); return; } @@ -71,13 +71,13 @@ const showActorDetails = (report) => { const actorAccountID = lodashGet(parentReportAction, 'actorAccountID', -1); // in an ideal situation account ID won't be 0 if (actorAccountID > 0) { - Navigation.navigate(ROUTES.getProfileRoute(actorAccountID)); + Navigation.navigate(ROUTES.PROFILE.getRoute(actorAccountID)); return; } } // report detail route is added as fallback but based on the current implementation this route won't be executed - Navigation.navigate(ROUTES.getReportDetailsRoute(report.reportID)); + Navigation.navigate(ROUTES.REPORT_WITH_ID_DETAILS.getRoute(report.reportID)); }; function AvatarWithDisplayName(props) { @@ -85,12 +85,13 @@ function AvatarWithDisplayName(props) { const subtitle = ReportUtils.getChatRoomSubtitle(props.report); const parentNavigationSubtitleData = ReportUtils.getParentNavigationSubtitle(props.report); const isMoneyRequestOrReport = ReportUtils.isMoneyRequestReport(props.report) || ReportUtils.isMoneyRequest(props.report); - const icons = ReportUtils.getIcons(props.report, props.personalDetails, props.policy, true); + const icons = ReportUtils.getIcons(props.report, props.personalDetails, props.policy); const ownerPersonalDetails = OptionsListUtils.getPersonalDetailsForAccountIDs([props.report.ownerAccountID], props.personalDetails); const displayNamesWithTooltips = ReportUtils.getDisplayNamesWithTooltips(_.values(ownerPersonalDetails), false); const shouldShowSubscriptAvatar = ReportUtils.shouldReportShowSubscript(props.report); const isExpenseRequest = ReportUtils.isExpenseRequest(props.report); const defaultSubscriptSize = isExpenseRequest ? CONST.AVATAR_SIZE.SMALL_NORMAL : props.size; + const avatarBorderColor = props.isAnonymous ? themeColors.highlightBG : themeColors.componentBG; return ( @@ -103,7 +104,7 @@ function AvatarWithDisplayName(props) { > {shouldShowSubscriptAvatar ? ( )} diff --git a/src/components/AvatarWithImagePicker.js b/src/components/AvatarWithImagePicker.js index aa50d6db574b..a44d1841bbb6 100644 --- a/src/components/AvatarWithImagePicker.js +++ b/src/components/AvatarWithImagePicker.js @@ -21,8 +21,11 @@ import stylePropTypes from '../styles/stylePropTypes'; import * as FileUtils from '../libs/fileDownload/FileUtils'; import getImageResolution from '../libs/fileDownload/getImageResolution'; import PressableWithoutFeedback from './Pressable/PressableWithoutFeedback'; +import AttachmentModal from './AttachmentModal'; import DotIndicatorMessage from './DotIndicatorMessage'; import * as Browser from '../libs/Browser'; +import withNavigationFocus, {withNavigationFocusPropTypes} from './withNavigationFocus'; +import compose from '../libs/compose'; const propTypes = { /** Avatar source to display */ @@ -58,7 +61,7 @@ const propTypes = { size: PropTypes.oneOf([CONST.AVATAR_SIZE.LARGE, CONST.AVATAR_SIZE.DEFAULT]), /** A fallback avatar icon to display when there is an error on loading avatar from remote URL. */ - fallbackIcon: PropTypes.func, + fallbackIcon: PropTypes.oneOfType([PropTypes.func, PropTypes.string]), /** Denotes whether it is an avatar or a workspace avatar */ type: PropTypes.oneOf([CONST.ICON_TYPE_AVATAR, CONST.ICON_TYPE_WORKSPACE]), @@ -79,7 +82,17 @@ const propTypes = { // eslint-disable-next-line react/forbid-prop-types errors: PropTypes.object, + /** Title for avatar preview modal */ + headerTitle: PropTypes.string, + + /** Avatar source for avatar preview modal */ + previewSource: PropTypes.oneOfType([PropTypes.string, PropTypes.func]), + + /** File name of the avatar */ + originalFileName: PropTypes.string, + ...withLocalizePropTypes, + ...withNavigationFocusPropTypes, }; const defaultProps = { @@ -98,6 +111,9 @@ const defaultProps = { onErrorClose: () => {}, pendingAction: null, errors: null, + headerTitle: '', + previewSource: '', + originalFileName: '', }; class AvatarWithImagePicker extends React.Component { @@ -129,6 +145,9 @@ class AvatarWithImagePicker extends React.Component { } componentDidUpdate(prevProps) { + if (!prevProps.isFocused && this.props.isFocused) { + this.setError(null, {}); + } if (!prevProps.isUploading && this.props.isUploading) { this.animation.start(); } else if (prevProps.isUploading && !this.props.isUploading) { @@ -273,58 +292,73 @@ class AvatarWithImagePicker extends React.Component { - - {({openPicker}) => { - const menuItems = [ - { - icon: Expensicons.Upload, - text: this.props.translate('avatarWithImagePicker.uploadPhoto'), - onSelected: () => { - if (Browser.isSafari()) { - return; - } - openPicker({ - onPicked: this.showAvatarCropModal, + + {({show}) => ( + + {({openPicker}) => { + const menuItems = [ + { + icon: Expensicons.Upload, + text: this.props.translate('avatarWithImagePicker.uploadPhoto'), + onSelected: () => { + if (Browser.isSafari()) { + return; + } + openPicker({ + onPicked: this.showAvatarCropModal, + }); + }, + }, + ]; + + // If current avatar isn't a default avatar, allow Remove Photo option + if (!this.props.isUsingDefaultAvatar) { + menuItems.push({ + icon: Expensicons.Trashcan, + text: this.props.translate('avatarWithImagePicker.removePhoto'), + onSelected: () => { + this.setError(null, {}); + this.props.onImageRemoved(); + }, + }); + + menuItems.push({ + icon: Expensicons.Eye, + text: this.props.translate('avatarWithImagePicker.viewPhoto'), + onSelected: () => show(), }); - }, - }, - ]; - - // If current avatar isn't a default avatar, allow Remove Photo option - if (!this.props.isUsingDefaultAvatar) { - menuItems.push({ - icon: Expensicons.Trashcan, - text: this.props.translate('avatarWithImagePicker.removePhoto'), - onSelected: () => { - this.setError(null, {}); - this.props.onImageRemoved(); - }, - }); - } - return ( - this.setState({isMenuVisible: false})} - onItemSelected={(item, index) => { - this.setState({isMenuVisible: false}); - // In order for the file picker to open dynamically, the click - // function must be called from within a event handler that was initiated - // by the user on Safari. - if (index === 0 && Browser.isSafari()) { - openPicker({ - onPicked: this.showAvatarCropModal, - }); - } - }} - menuItems={menuItems} - anchorPosition={this.props.anchorPosition} - withoutOverlay - anchorRef={this.anchorRef} - anchorAlignment={this.props.anchorAlignment} - /> - ); - }} - + } + return ( + this.setState({isMenuVisible: false})} + onItemSelected={(item, index) => { + this.setState({isMenuVisible: false}); + // In order for the file picker to open dynamically, the click + // function must be called from within a event handler that was initiated + // by the user on Safari. + if (index === 0 && Browser.isSafari()) { + openPicker({ + onPicked: this.showAvatarCropModal, + }); + } + }} + menuItems={menuItems} + anchorPosition={this.props.anchorPosition} + withoutOverlay + anchorRef={this.anchorRef} + anchorAlignment={this.props.anchorAlignment} + /> + ); + }} + + )} + {this.state.validationError && ( - + diff --git a/src/components/BaseMiniContextMenuItem.js b/src/components/BaseMiniContextMenuItem.js index acf5d165d7c7..0e9085b54c17 100644 --- a/src/components/BaseMiniContextMenuItem.js +++ b/src/components/BaseMiniContextMenuItem.js @@ -8,6 +8,8 @@ import getButtonState from '../libs/getButtonState'; import variables from '../styles/variables'; import Tooltip from './Tooltip'; import PressableWithoutFeedback from './Pressable/PressableWithoutFeedback'; +import ReportActionComposeFocusManager from '../libs/ReportActionComposeFocusManager'; +import DomUtils from '../libs/DomUtils'; const propTypes = { /** @@ -53,7 +55,14 @@ function BaseMiniContextMenuItem(props) { e.preventDefault()} + onMouseDown={(e) => { + if (!ReportActionComposeFocusManager.isFocused() && !ReportActionComposeFocusManager.isEditFocused()) { + DomUtils.getActiveElement().blur(); + return; + } + + e.preventDefault(); + }} accessibilityLabel={props.tooltipText} style={({hovered, pressed}) => [ styles.reportActionContextMenuMiniButton, diff --git a/src/components/BlockingViews/FullPageNotFoundView.js b/src/components/BlockingViews/FullPageNotFoundView.js index 54bdc015de37..a9c4bf63b65e 100644 --- a/src/components/BlockingViews/FullPageNotFoundView.js +++ b/src/components/BlockingViews/FullPageNotFoundView.js @@ -8,6 +8,7 @@ import Navigation from '../../libs/Navigation/Navigation'; import variables from '../../styles/variables'; import styles from '../../styles/styles'; import useLocalize from '../../hooks/useLocalize'; +import ROUTES from '../../ROUTES'; const propTypes = { /** Child elements */ @@ -44,7 +45,7 @@ const defaultProps = { titleKey: 'notFound.notHere', subtitleKey: 'notFound.pageNotFound', linkKey: 'notFound.goBackHome', - onBackButtonPress: Navigation.goBack, + onBackButtonPress: () => Navigation.goBack(ROUTES.HOME), shouldShowLink: true, shouldShowBackButton: true, onLinkPress: () => Navigation.dismissModal(), diff --git a/src/components/Button/index.js b/src/components/Button/index.js index c16860344837..4ca933a45d6f 100644 --- a/src/components/Button/index.js +++ b/src/components/Button/index.js @@ -145,7 +145,7 @@ const defaultProps = { style: [], innerStyles: [], textStyles: [], - shouldUseDefaultHover: false, + shouldUseDefaultHover: true, success: false, danger: false, children: null, @@ -306,6 +306,7 @@ class Button extends Component { ]} nativeID={this.props.nativeID} accessibilityLabel={this.props.accessibilityLabel} + accessibilityRole={CONST.ACCESSIBILITY_ROLE.BUTTON} hoverDimmingValue={1} > {this.renderContent()} diff --git a/src/components/ButtonWithDropdownMenu.js b/src/components/ButtonWithDropdownMenu.js index 62eeb3030619..54d6c0deac5a 100644 --- a/src/components/ButtonWithDropdownMenu.js +++ b/src/components/ButtonWithDropdownMenu.js @@ -32,7 +32,7 @@ const propTypes = { style: PropTypes.oneOfType([PropTypes.arrayOf(PropTypes.object), PropTypes.object]), /** Menu options to display */ - /** e.g. [{text: 'Pay with Expensify', icon: Wallet}, {text: 'PayPal', icon: PayPal}] */ + /** e.g. [{text: 'Pay with Expensify', icon: Wallet}] */ options: PropTypes.arrayOf( PropTypes.shape({ value: PropTypes.string.isRequired, diff --git a/src/components/CardPreview.js b/src/components/CardPreview.js new file mode 100644 index 000000000000..4f774d67360c --- /dev/null +++ b/src/components/CardPreview.js @@ -0,0 +1,68 @@ +import React from 'react'; +import {View} from 'react-native'; +import {withOnyx} from 'react-native-onyx'; +import PropTypes from 'prop-types'; +import styles from '../styles/styles'; +import Text from './Text'; +import usePrivatePersonalDetails from '../hooks/usePrivatePersonalDetails'; +import ONYXKEYS from '../ONYXKEYS'; +import ExpensifyCardImage from '../../assets/images/expensify-card.svg'; +import variables from '../styles/variables'; + +const propTypes = { + /** User's private personal details */ + privatePersonalDetails: PropTypes.shape({ + legalFirstName: PropTypes.string, + legalLastName: PropTypes.string, + }), + /** Session info for the currently logged in user. */ + session: PropTypes.shape({ + /** Currently logged-in user email */ + email: PropTypes.string, + }), +}; + +const defaultProps = { + privatePersonalDetails: { + legalFirstName: '', + legalLastName: '', + }, + session: { + email: '', + }, +}; + +function CardPreview({privatePersonalDetails: {legalFirstName, legalLastName}, session: {email}}) { + usePrivatePersonalDetails(); + const cardHolder = legalFirstName && legalLastName ? `${legalFirstName} ${legalLastName}` : email; + + return ( + + + + {cardHolder} + + + ); +} + +CardPreview.propTypes = propTypes; +CardPreview.defaultProps = defaultProps; +CardPreview.displayName = 'CardPreview'; + +export default withOnyx({ + privatePersonalDetails: { + key: ONYXKEYS.PRIVATE_PERSONAL_DETAILS, + }, + session: { + key: ONYXKEYS.SESSION, + }, +})(CardPreview); diff --git a/src/components/CategoryPicker/categoryPickerPropTypes.js b/src/components/CategoryPicker/categoryPickerPropTypes.js index b8e24c199a73..6f2800a5d98f 100644 --- a/src/components/CategoryPicker/categoryPickerPropTypes.js +++ b/src/components/CategoryPicker/categoryPickerPropTypes.js @@ -2,14 +2,11 @@ import PropTypes from 'prop-types'; import categoryPropTypes from '../categoryPropTypes'; const propTypes = { - /** The report ID of the IOU */ - reportID: PropTypes.string.isRequired, - /** The policyID we are getting categories for */ policyID: PropTypes.string, - /** The type of IOU report, i.e. bill, request, send */ - iouType: PropTypes.string.isRequired, + /** The selected category of an expense */ + selectedCategory: PropTypes.string, /* Onyx Props */ /** Collection of categories attached to a policy */ @@ -19,18 +16,15 @@ const propTypes = { /** Collection of recently used categories attached to a policy */ policyRecentlyUsedCategories: PropTypes.arrayOf(PropTypes.string), - /* Onyx Props */ - /** Holds data related to Money Request view state, rather than the underlying Money Request data. */ - iou: PropTypes.shape({ - category: PropTypes.string.isRequired, - }), + /** Callback to fire when a category is pressed */ + onSubmit: PropTypes.func.isRequired, }; const defaultProps = { policyID: '', + selectedCategory: '', policyCategories: {}, policyRecentlyUsedCategories: [], - iou: {}, }; export {propTypes, defaultProps}; diff --git a/src/components/CategoryPicker/index.js b/src/components/CategoryPicker/index.js index 91c7e82e7887..ef8b1d71ad1d 100644 --- a/src/components/CategoryPicker/index.js +++ b/src/components/CategoryPicker/index.js @@ -5,67 +5,65 @@ import lodashGet from 'lodash/get'; import ONYXKEYS from '../../ONYXKEYS'; import {propTypes, defaultProps} from './categoryPickerPropTypes'; import styles from '../../styles/styles'; -import Navigation from '../../libs/Navigation/Navigation'; -import ROUTES from '../../ROUTES'; import CONST from '../../CONST'; -import * as IOU from '../../libs/actions/IOU'; import * as OptionsListUtils from '../../libs/OptionsListUtils'; import OptionsSelector from '../OptionsSelector'; import useLocalize from '../../hooks/useLocalize'; -function CategoryPicker({policyCategories, reportID, iouType, iou, policyRecentlyUsedCategories}) { +function CategoryPicker({selectedCategory, policyCategories, policyRecentlyUsedCategories, onSubmit}) { const {translate} = useLocalize(); const [searchValue, setSearchValue] = useState(''); - const policyCategoriesCount = _.size(policyCategories); + const policyCategoriesCount = OptionsListUtils.getEnabledCategoriesCount(_.values(policyCategories)); const isCategoriesCountBelowThreshold = policyCategoriesCount < CONST.CATEGORY_LIST_THRESHOLD; const selectedOptions = useMemo(() => { - if (!iou.category) { + if (!selectedCategory) { return []; } return [ { - name: iou.category, + name: selectedCategory, enabled: true, accountID: null, }, ]; - }, [iou.category]); + }, [selectedCategory]); - const initialFocusedIndex = useMemo(() => { - if (isCategoriesCountBelowThreshold && selectedOptions.length > 0) { - return _.chain(policyCategories) - .values() - .findIndex((category) => category.name === selectedOptions[0].name, true) - .value(); - } - - return 0; - }, [policyCategories, selectedOptions, isCategoriesCountBelowThreshold]); + const sections = useMemo(() => { + const {categoryOptions} = OptionsListUtils.getFilteredOptions( + {}, + {}, + [], + searchValue, + selectedOptions, + [], + false, + false, + true, + policyCategories, + policyRecentlyUsedCategories, + false, + ); - const sections = useMemo( - () => OptionsListUtils.getNewChatOptions({}, {}, [], searchValue, selectedOptions, [], false, false, true, policyCategories, policyRecentlyUsedCategories, false).categoryOptions, - [policyCategories, policyRecentlyUsedCategories, searchValue, selectedOptions], - ); + return categoryOptions; + }, [policyCategories, policyRecentlyUsedCategories, searchValue, selectedOptions]); - const headerMessage = OptionsListUtils.getHeaderMessage(lodashGet(sections, '[0].data.length', 0) > 0, false, searchValue); - const shouldShowTextInput = !isCategoriesCountBelowThreshold; + const initialFocusedIndex = useMemo(() => { + let categoryInitialFocusedIndex = 0; - const navigateBack = () => { - Navigation.goBack(ROUTES.getMoneyRequestConfirmationRoute(iouType, reportID)); - }; + if (!_.isEmpty(searchValue) || isCategoriesCountBelowThreshold) { + const index = _.findIndex(lodashGet(sections, '[0].data', []), (category) => category.searchText === selectedCategory); - const updateCategory = (category) => { - if (category.searchText === iou.category) { - IOU.resetMoneyRequestCategory(); - } else { - IOU.setMoneyRequestCategory(category.searchText); + categoryInitialFocusedIndex = index === -1 ? 0 : index; } - navigateBack(); - }; + return categoryInitialFocusedIndex; + }, [selectedCategory, searchValue, isCategoriesCountBelowThreshold, sections]); + + const headerMessage = OptionsListUtils.getHeaderMessage(lodashGet(sections, '[0].data.length', 0) > 0, false, searchValue); + const shouldShowTextInput = !isCategoriesCountBelowThreshold; return ( ); } @@ -97,7 +95,4 @@ export default withOnyx({ policyRecentlyUsedCategories: { key: ({policyID}) => `${ONYXKEYS.COLLECTION.POLICY_RECENTLY_USED_CATEGORIES}${policyID}`, }, - iou: { - key: ONYXKEYS.IOU, - }, })(CategoryPicker); diff --git a/src/components/Composer/index.android.js b/src/components/Composer/index.android.js index d0805cbcc7c3..1132efa9e50e 100644 --- a/src/components/Composer/index.android.js +++ b/src/components/Composer/index.android.js @@ -97,7 +97,9 @@ function Composer({shouldClear, onClear, isDisabled, maxLines, forwardedRef, isC * @return {Number} */ const maxNumberOfLines = useMemo(() => { - if (isComposerFullSize) return 1000000; + if (isComposerFullSize) { + return 1000000; + } return maxLines; }, [isComposerFullSize, maxLines]); diff --git a/src/components/Composer/index.ios.js b/src/components/Composer/index.ios.js index c0a3859e6d01..0b2c93f6639e 100644 --- a/src/components/Composer/index.ios.js +++ b/src/components/Composer/index.ios.js @@ -97,7 +97,9 @@ function Composer({shouldClear, onClear, isDisabled, maxLines, forwardedRef, isC * @return {Number} */ const maxNumberOfLines = useMemo(() => { - if (isComposerFullSize) return undefined; + if (isComposerFullSize) { + return; + } return maxLines; }, [isComposerFullSize, maxLines]); diff --git a/src/components/ConfirmContent.js b/src/components/ConfirmContent.js index ab3e23d6b1c1..469efb4f25d9 100644 --- a/src/components/ConfirmContent.js +++ b/src/components/ConfirmContent.js @@ -133,7 +133,6 @@ function ConfirmContent(props) { style={[styles.mt3, styles.noSelect]} onPress={props.onCancel} text={props.cancelText || translate('common.no')} - shouldUseDefaultHover /> )} @@ -144,7 +143,6 @@ function ConfirmContent(props) { style={[styles.noSelect, styles.flex1]} onPress={props.onCancel} text={props.cancelText || translate('common.no')} - shouldUseDefaultHover medium /> )} diff --git a/src/components/ConfirmedRoute.js b/src/components/ConfirmedRoute.js index 4bcdc4738a3c..dab30e60ca55 100644 --- a/src/components/ConfirmedRoute.js +++ b/src/components/ConfirmedRoute.js @@ -1,9 +1,9 @@ import React, {useEffect} from 'react'; import PropTypes from 'prop-types'; -import {View} from 'react-native'; import {withOnyx} from 'react-native-onyx'; import lodashGet from 'lodash/get'; +import lodashIsNil from 'lodash/isNil'; import _ from 'underscore'; import ONYXKEYS from '../ONYXKEYS'; import CONST from '../CONST'; @@ -13,9 +13,8 @@ import * as Expensicons from './Icon/Expensicons'; import theme from '../styles/themes/default'; import styles from '../styles/styles'; import transactionPropTypes from './transactionPropTypes'; -import BlockingView from './BlockingViews/BlockingView'; +import PendingMapView from './MapView/PendingMapView'; import useNetwork from '../hooks/useNetwork'; -import useLocalize from '../hooks/useLocalize'; import DistanceMapView from './DistanceMapView'; const propTypes = { @@ -44,7 +43,7 @@ const getWaypointMarkers = (waypoints) => { const lastWaypointIndex = numberOfWaypoints - 1; return _.filter( _.map(waypoints, (waypoint, key) => { - if (!waypoint || waypoint.lng === undefined || waypoint.lat === undefined) { + if (!waypoint || lodashIsNil(waypoint.lat) || lodashIsNil(waypoint.lng)) { return; } @@ -76,7 +75,6 @@ const getWaypointMarkers = (waypoints) => { function ConfirmedRoute({mapboxAccessToken, transaction}) { const {isOffline} = useNetwork(); - const {translate} = useLocalize(); const {route0: route} = transaction.routes || {}; const waypoints = lodashGet(transaction, 'comment.waypoints', {}); const coordinates = lodashGet(route, 'geometry.coordinates', []); @@ -104,14 +102,7 @@ function ConfirmedRoute({mapboxAccessToken, transaction}) { styleURL={CONST.MAPBOX.STYLE_URL} /> ) : ( - - - + )} ); diff --git a/src/components/ContextMenuItem.js b/src/components/ContextMenuItem.js index c7ca3f948da4..2314f2fcf64e 100644 --- a/src/components/ContextMenuItem.js +++ b/src/components/ContextMenuItem.js @@ -1,4 +1,4 @@ -import React from 'react'; +import React, {forwardRef, useImperativeHandle} from 'react'; import PropTypes from 'prop-types'; import MenuItem from './MenuItem'; import Icon from './Icon'; @@ -34,6 +34,12 @@ const propTypes = { /** The action accept for anonymous user or not */ isAnonymousAction: PropTypes.bool, + + /** Whether the menu item is focused or not */ + isFocused: PropTypes.bool, + + /** Forwarded ref to ContextMenuItem */ + innerRef: PropTypes.oneOfType([PropTypes.func, PropTypes.object]), }; const defaultProps = { @@ -42,9 +48,11 @@ const defaultProps = { successText: '', description: '', isAnonymousAction: false, + isFocused: false, + innerRef: null, }; -function ContextMenuItem({onPress, successIcon, successText, icon, text, isMini, description, isAnonymousAction}) { +function ContextMenuItem({onPress, successIcon, successText, icon, text, isMini, description, isAnonymousAction, isFocused, innerRef}) { const {windowWidth} = useWindowDimensions(); const [isThrottledButtonActive, setThrottledButtonInactive] = useThrottledButtonState(); @@ -61,6 +69,8 @@ function ContextMenuItem({onPress, successIcon, successText, icon, text, isMini, } }; + useImperativeHandle(innerRef, () => ({triggerPressAndUpdateSuccess})); + const itemIcon = !isThrottledButtonActive && successIcon ? successIcon : icon; const itemText = !isThrottledButtonActive && successText ? successText : text; @@ -89,6 +99,7 @@ function ContextMenuItem({onPress, successIcon, successText, icon, text, isMini, descriptionTextStyle={styles.breakAll} style={getContextMenuItemStyles(windowWidth)} isAnonymousAction={isAnonymousAction} + focused={isFocused} /> ); } @@ -97,4 +108,10 @@ ContextMenuItem.propTypes = propTypes; ContextMenuItem.defaultProps = defaultProps; ContextMenuItem.displayName = 'ContextMenuItem'; -export default ContextMenuItem; +export default forwardRef((props, ref) => ( + +)); diff --git a/src/components/CountryPicker/CountrySelectorModal.js b/src/components/CountryPicker/CountrySelectorModal.js index ac543d9921d2..6c6cd19af0c7 100644 --- a/src/components/CountryPicker/CountrySelectorModal.js +++ b/src/components/CountryPicker/CountrySelectorModal.js @@ -78,6 +78,7 @@ function CountrySelectorModal({currentCountry, isVisible, onClose, onCountrySele style={[styles.pb0]} includePaddingTop={false} includeSafeAreaPaddingBottom={false} + testID={CountrySelectorModal.displayName} > { - onInputChange(country.value); + if (country.value !== value) { + onInputChange(country.value); + } hidePickerModal(); }; diff --git a/src/components/CurrentUserPersonalDetailsSkeletonView/index.js b/src/components/CurrentUserPersonalDetailsSkeletonView/index.js index 6e6c46e971c0..cc305a628820 100644 --- a/src/components/CurrentUserPersonalDetailsSkeletonView/index.js +++ b/src/components/CurrentUserPersonalDetailsSkeletonView/index.js @@ -1,5 +1,6 @@ import React from 'react'; import PropTypes from 'prop-types'; +import _ from 'underscore'; import SkeletonViewContentLoader from 'react-content-loader/native'; import {Circle, Rect} from 'react-native-svg'; import {View} from 'react-native'; @@ -12,14 +13,26 @@ import styles from '../../styles/styles'; const propTypes = { /** Whether to animate the skeleton view */ shouldAnimate: PropTypes.bool, + + /** The size of the avatar */ + avatarSize: PropTypes.oneOf(_.values(CONST.AVATAR_SIZE)), + + /** Background color of the skeleton view */ + backgroundColor: PropTypes.string, + + /** Foreground color of the skeleton view */ + foregroundColor: PropTypes.string, }; const defaultProps = { shouldAnimate: true, + avatarSize: CONST.AVATAR_SIZE.LARGE, + backgroundColor: themeColors.highlightBG, + foregroundColor: themeColors.border, }; function CurrentUserPersonalDetailsSkeletonView(props) { - const avatarPlaceholderSize = StyleUtils.getAvatarSize(CONST.AVATAR_SIZE.LARGE); + const avatarPlaceholderSize = StyleUtils.getAvatarSize(props.avatarSize); const avatarPlaceholderRadius = avatarPlaceholderSize / 2; const spaceBetweenAvatarAndHeadline = styles.mb3.marginBottom + styles.mt1.marginTop + (variables.lineHeightXXLarge - variables.fontSizeXLarge) / 2; const headlineSize = variables.fontSizeXLarge; @@ -29,8 +42,8 @@ function CurrentUserPersonalDetailsSkeletonView(props) { 1; + const isRouteAbsentWithoutErrors = !hasRoute && !hasRouteError; + const shouldFetchRoute = (isRouteAbsentWithoutErrors || haveValidatedWaypointsChanged) && !isLoadingRoute && _.size(validatedWaypoints) > 1; const waypointMarkers = useMemo( () => _.filter( _.map(waypoints, (waypoint, key) => { - if (!waypoint || !lodashHas(waypoint, 'lat') || !lodashHas(waypoint, 'lng') || lodashIsNull(waypoint.lat) || lodashIsNull(waypoint.lng)) { + if (!waypoint || lodashIsNil(waypoint.lat) || lodashIsNil(waypoint.lng)) { return; } @@ -189,12 +189,12 @@ function DistanceRequest({iou, iouType, report, transaction, mapboxAccessToken, useEffect(updateGradientVisibility, [scrollContainerHeight, scrollContentHeight]); const navigateBack = () => { - Navigation.goBack(isEditing ? ROUTES.getMoneyRequestConfirmationRoute(iouType, reportID) : null); + Navigation.goBack(isEditing ? ROUTES.MONEY_REQUEST_CONFIRMATION.getRoute(iouType, reportID) : ROUTES.HOME); }; const navigateToNextPage = () => { if (isEditing) { - Navigation.goBack(ROUTES.getMoneyRequestConfirmationRoute(iouType, reportID)); + Navigation.goBack(ROUTES.MONEY_REQUEST_CONFIRMATION.getRoute(iouType, reportID)); return; } @@ -237,7 +237,7 @@ function DistanceRequest({iou, iouType, report, transaction, mapboxAccessToken, secondaryIcon={waypointIcon} secondaryIconFill={theme.icon} shouldShowRightIcon - onPress={() => Navigation.navigate(ROUTES.getMoneyRequestWaypointRoute('request', index))} + onPress={() => Navigation.navigate(ROUTES.MONEY_REQUEST_WAYPOINT.getRoute('request', index))} key={key} /> ); @@ -261,7 +261,10 @@ function DistanceRequest({iou, iouType, report, transaction, mapboxAccessToken,