lint.sh 2.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110
  1. #!/usr/bin/env bash
  2. #
  3. # Runs linting scripts over the local Synapse checkout
  4. # isort - sorts import statements
  5. # black - opinionated code formatter
  6. # flake8 - lints and finds mistakes
  7. set -e
  8. usage() {
  9. echo
  10. echo "Usage: $0 [-h] [-d] [paths...]"
  11. echo
  12. echo "-d"
  13. echo " Lint files that have changed since the last git commit."
  14. echo
  15. echo " If paths are provided and this option is set, both provided paths and those"
  16. echo " that have changed since the last commit will be linted."
  17. echo
  18. echo " If no paths are provided and this option is not set, all files will be linted."
  19. echo
  20. echo " Note that paths with a file extension that is not '.py' will be excluded."
  21. echo "-h"
  22. echo " Display this help text."
  23. }
  24. USING_DIFF=0
  25. files=()
  26. while getopts ":dh" opt; do
  27. case $opt in
  28. d)
  29. USING_DIFF=1
  30. ;;
  31. h)
  32. usage
  33. exit
  34. ;;
  35. \?)
  36. echo "ERROR: Invalid option: -$OPTARG" >&2
  37. usage
  38. exit
  39. ;;
  40. esac
  41. done
  42. # Strip any options from the command line arguments now that
  43. # we've finished processing them
  44. shift "$((OPTIND-1))"
  45. if [ $USING_DIFF -eq 1 ]; then
  46. # Check both staged and non-staged changes
  47. for path in $(git diff HEAD --name-only); do
  48. filename=$(basename "$path")
  49. file_extension="${filename##*.}"
  50. # If an extension is present, and it's something other than 'py',
  51. # then ignore this file
  52. if [[ -n ${file_extension+x} && $file_extension != "py" ]]; then
  53. continue
  54. fi
  55. # Append this path to our list of files to lint
  56. files+=("$path")
  57. done
  58. fi
  59. # Append any remaining arguments as files to lint
  60. files+=("$@")
  61. if [[ $USING_DIFF -eq 1 ]]; then
  62. # If we were asked to lint changed files, and no paths were found as a result...
  63. if [ ${#files[@]} -eq 0 ]; then
  64. # Then print and exit
  65. echo "No files found to lint."
  66. exit 0
  67. fi
  68. else
  69. # If we were not asked to lint changed files, and no paths were found as a result,
  70. # then lint everything!
  71. if [[ -z ${files+x} ]]; then
  72. # CI runs each linter on the entire checkout, e.g. `black .`. So don't
  73. # rely on this list to *find* lint targets if that misses a file; instead;
  74. # use it to exclude files from linters when this can't be done by config.
  75. #
  76. # To check which files the linters examine, use:
  77. # black --verbose . 2>&1 | \grep -v ignored
  78. # isort --show-files .
  79. # flake8 --verbose . # This isn't a great option
  80. # mypy has explicit config in mypy.ini; there is also mypy --verbose
  81. files=(
  82. "synapse" "docker" "tests"
  83. "scripts-dev"
  84. "contrib" "synmark" "stubs" ".ci"
  85. )
  86. fi
  87. fi
  88. echo "Linting these paths: ${files[*]}"
  89. echo
  90. # Print out the commands being run
  91. set -x
  92. isort "${files[@]}"
  93. python3 -m black "${files[@]}"
  94. ./scripts-dev/config-lint.sh
  95. flake8 "${files[@]}"
  96. ./scripts-dev/check_pydantic_models.py lint
  97. mypy