From ff5b83916c3f82ffcef13b7c915bb9240f629049 Mon Sep 17 00:00:00 2001 From: Kostiantyn <32730812+kkovaletp@users.noreply.github.com> Date: Tue, 19 Aug 2025 16:34:46 +0300 Subject: [PATCH] A few small fixes for bugs, detected during the merge upstream changes to my forked repo (#1270) * Migrate GolangCI config to the latest version; fix nll-pointer exception in the external EXIF parser and order of GPS coords in the internal one; updated links in Readme and added missing LibHeif exports * Improve GPS error handling --------- Co-authored-by: Konstantin Koval --- README.md | 12 +- api/.golangci.yml | 359 +++++------------------ api/scanner/exif/exif_parser_external.go | 13 +- api/scanner/exif/exif_parser_internal.go | 2 +- 4 files changed, 96 insertions(+), 290 deletions(-) diff --git a/README.md b/README.md index 4bddc9c9..f5bd7b87 100644 --- a/README.md +++ b/README.md @@ -1,8 +1,8 @@ photoview logo -[![License](https://img.shields.io/github/license/viktorstrate/photoview)](./LICENSE.txt) -[![GitHub contributors](https://img.shields.io/github/contributors/viktorstrate/photoview)](https://github.com/viktorstrate/photoview/graphs/contributors) -[![Docker Pulls](https://img.shields.io/docker/pulls/viktorstrate/photoview)](https://hub.docker.com/r/viktorstrate/photoview) +[![License](https://img.shields.io/github/license/photoview/photoview)](./LICENSE.txt) +[![GitHub contributors](https://img.shields.io/github/contributors/photoview/photoview)](https://github.com/photoview/photoview/graphs/contributors) +[![Docker Pulls](https://img.shields.io/docker/pulls/photoview/photoview)](https://hub.docker.com/r/photoview/photoview) [![Docker builds](https://github.com/photoview/photoview/actions/workflows/build.yml/badge.svg?branch=master)](https://github.com/photoview/photoview/actions/workflows/build.yml) [![codecov](https://codecov.io/gh/photoview/photoview/branch/master/graph/badge.svg?token=AATZKC93F7)](https://codecov.io/gh/photoview/photoview) @@ -333,9 +333,9 @@ Then run the following commands: $ source ./scripts/set_compiler_env.sh # Set the compiler environment with `homebrew` $ export CPLUS_INCLUDE_PATH="$(brew --prefix)/opt/jpeg/include:$(brew --prefix)/opt/dlib/include:${CPLUS_INCLUDE_PATH:-}" -$ export C_INCLUDE_PATH="$(brew --prefix)/opt/libmagic/include:${C_INCLUDE_PATH:-}" -$ export DYLD_LIBRARY_PATH="$(brew --prefix)/opt/jpeg/lib:$(brew --prefix)/opt/dlib/lib:$(brew --prefix)/opt/libmagic/lib:${DYLD_LIBRARY_PATH:-}" -$ export LIBRARY_PATH="$(brew --prefix)/opt/jpeg/lib:$(brew --prefix)/opt/dlib/lib:$(brew --prefix)/opt/libmagic/lib:${LIBRARY_PATH:-}" +$ export C_INCLUDE_PATH="$(brew --prefix)/opt/libmagic/include:$(brew --prefix)/opt/libheif/include:${C_INCLUDE_PATH:-}" +$ export DYLD_LIBRARY_PATH="$(brew --prefix)/opt/jpeg/lib:$(brew --prefix)/opt/dlib/lib:$(brew --prefix)/opt/libmagic/lib:$(brew --prefix)/opt/libheif/lib:${DYLD_LIBRARY_PATH:-}" +$ export LIBRARY_PATH="$(brew --prefix)/opt/jpeg/lib:$(brew --prefix)/opt/dlib/lib:$(brew --prefix)/opt/libmagic/lib:$(brew --prefix)/opt/libheif/lib:${LIBRARY_PATH:-}" $ export CGO_CFLAGS_ALLOW=-Xpreprocessor # Start API server $ cd ./api diff --git a/api/.golangci.yml b/api/.golangci.yml index ab6a579b..8bd83c59 100644 --- a/api/.golangci.yml +++ b/api/.golangci.yml @@ -1,301 +1,98 @@ -# Options for analysis running. +version: "2" run: - # Number of operating system threads (`GOMAXPROCS`) that can execute golangci-lint simultaneously. - # If it is explicitly set to 0 (i.e. not the default) then golangci-lint will automatically set the value to match Linux container CPU quota. - # Default: the number of logical CPUs in the machine - #concurrency: 4 - # Timeout for analysis, e.g. 30s, 5m. - # Default: 1m - #timeout: 5m - # Exit code when at least one issue was found. - # Default: 1 - #issues-exit-code: 2 - # Include test files or not. - # Default: true tests: false - # List of build tags, all linters use it. - # Default: [] - #build-tags: - # - mytag - # If set, we pass it to "go list -mod={option}". From "go help modules": - # If invoked with -mod=readonly, the go command is disallowed from the implicit - # automatic updating of go.mod described above. Instead, it fails when any changes - # to go.mod are needed. This setting is most useful to check that go.mod does - # not need updates, such as in a continuous integration and testing system. - # If invoked with -mod=vendor, the go command assumes that the vendor - # directory holds the correct copies of dependencies and ignores - # the dependency descriptions in go.mod. - # - # Allowed values: readonly|vendor|mod - # Default: "" - #modules-download-mode: readonly - # Allow multiple parallel golangci-lint instances running. - # If false, golangci-lint acquires file lock on start. - # Default: false allow-parallel-runners: true - # Allow multiple golangci-lint instances running, but serialize them around a lock. - # If false, golangci-lint exits with an error if it fails to acquire file lock on start. - # Default: false allow-serial-runners: true - # Define the Go version limit. - # Mainly related to generics support since go1.18. - # Default: use Go version from the go.mod file, fallback on the env var `GOVERSION`, fallback on 1.17 - #go: '1.19' - -# output configuration options output: - # The formats used to render issues. - # Formats: - # - `colored-line-number` - # - `line-number` - # - `json` - # - `colored-tab` - # - `tab` - # - `html` - # - `checkstyle` - # - `code-climate` - # - `junit-xml` - # - `github-actions` - # - `teamcity` - # - `sarif` - # Output path can be either `stdout`, `stderr` or path to the file to write to. - # - # For the CLI flag (`--out-format`), multiple formats can be specified by separating them by comma. - # The output can be specified for each of them by separating format name and path by colon symbol. - # Example: "--out-format=checkstyle:report.xml,json:stdout,colored-line-number" - # The CLI flag (`--out-format`) override the configuration file. - # - # Default: - # formats: - # - format: colored-line-number - # path: stdout formats: - - format: junit-xml + junit-xml: path: golang-lint.xml - - format: sarif + sarif: path: golang-lint.sarif - - format: github-actions - # Print lines of code with issue. - # Default: true - #print-issued-lines: false - # Print linter name in the end of issue text. - # Default: true - #print-linter-name: false - # Make issues output unique by line. - # Default: true - #uniq-by-line: false - # Add a prefix to the output file references. - # Default: "" - #path-prefix: "" - # Sort results by the order defined in `sort-order`. - # Default: false - sort-results: true - # Order to use when sorting results. - # Require `sort-results` to `true`. - # Possible values: `file`, `linter`, and `severity`. - # - # If the severity values are inside the following list, they are ordered in this order: - # 1. error - # 2. warning - # 3. high - # 4. medium - # 5. low - # Either they are sorted alphabetically. - # - # Default: ["file"] sort-order: - linter - severity - - file # filepath, line, and column. - # Show statistics per linter. - # Default: false - show-stats: true - + - file linters: - # Disable all linters. - # Default: false - #disable-all: true - # Enable specific linter - # https://golangci-lint.run/usage/linters/#enabled-by-default - #enable: {} - # Enable all available linters. - # Default: false - #enable-all: true - # Disable specific linter - # https://golangci-lint.run/usage/linters/#disabled-by-default - #disable: {} - # Enable presets. - # https://golangci-lint.run/usage/linters - # Default: [] - presets: - - bugs - - comment - - complexity - - error - - format - - import - - metalinter - - module - - performance - - sql - - style - # Enable only fast linters from enabled linters set (first run won't be fast) - # Default: false - fast: true + enable: + - asciicheck + - bidichk + - copyloopvar + - cyclop + - decorder + - depguard + - dogsled + - dupl + - dupword + - funlen + - gocheckcompilerdirectives + - gochecknoinits + - gocognit + - goconst + - gocyclo + - godot + - godox + - goheader + - gomoddirectives + - gomodguard + - goprintffuncname + - gosec + - grouper + - inamedparam + - interfacebloat + - lll + - maintidx + - misspell + - mnd + - nakedret + - nestif + - nlreturn + - nolintlint + - nosprintfhostport + - prealloc + - predeclared + - promlinter + - tagalign + - usestdlibvars + - whitespace + - wsl + disable: + - unused + exclusions: + rules: + - linters: + - dupl + - errcheck + - gocyclo + - gosec + path: _test\.go + - linters: + - forbidigo + path-except: _test\.go + - linters: + - lll + source: "^//go:generate " + paths: + - third_party$ + - builtin$ + - examples$ issues: - # List of regexps of issue texts to exclude. - # - # But independently of this option we use default exclude patterns, - # it can be disabled by `exclude-use-default: false`. - # To list all excluded by default patterns execute `golangci-lint run --help` - # - # Default: https://golangci-lint.run/usage/false-positives/#default-exclusions - #exclude: - #- abcdef - # Excluding configuration per-path, per-linter, per-text and per-source - exclude-rules: - # Exclude some linters from running on tests files. - - path: _test\.go - linters: - - gocyclo - - errcheck - - dupl - - gosec - # Run some linter only for test files by excluding its issues for everything else. - - path-except: _test\.go - linters: - - forbidigo - # Exclude known linters from partially hard-vendored code, - # which is impossible to exclude via `nolint` comments. - # `/` will be replaced by current OS file path separator to properly work on Windows. - #- path: internal/hmac/ - #text: "weak cryptographic primitive" - #linters: - #- gosec - # Exclude some `staticcheck` messages. - #- linters: - # - staticcheck - # text: "SA9003:" - # Exclude `lll` issues for long lines with `go:generate`. - - linters: - - lll - source: "^//go:generate " - # Independently of option `exclude` we use default exclude patterns, - # it can be disabled by this option. - # To list all excluded by default patterns execute `golangci-lint run --help`. - # Default: true - #exclude-use-default: false - # If set to true, `exclude` and `exclude-rules` regular expressions become case-sensitive. - # Default: false - exclude-case-sensitive: false - # Which dirs to exclude: issues from them won't be reported. - # Can use regexp here: `generated.*`, regexp is applied on full path, - # including the path prefix if one is set. - # Default dirs are skipped independently of this option's value (see exclude-dirs-use-default). - # "/" will be replaced by current OS file path separator to properly work on Windows. - # Default: [] - #exclude-dirs: - # - src/external_libs - # - autogenerated_by_my_lib - # Enables exclude of directories: - # - vendor$, third_party$, testdata$, examples$, Godeps$, builtin$ - # Default: true - #exclude-dirs-use-default: false - # Which files to exclude: they will be analyzed, but issues from them won't be reported. - # There is no need to include all autogenerated files, - # we confidently recognize autogenerated files. - # If it's not, please let us know. - # "/" will be replaced by current OS file path separator to properly work on Windows. - # Default: [] - #exclude-files: - # - ".*\\.my\\.go$" - # - lib/bad.go - # Mode of the generated files analysis. - # - # - `strict`: sources are excluded by following strictly the Go generated file convention. - # Source files that have lines matching only the following regular expression will be excluded: `^// Code generated .* DO NOT EDIT\.$` - # This line must appear before the first non-comment, non-blank text in the file. - # https://go.dev/s/generatedcode - # - `lax`: sources are excluded if they contain lines `autogenerated file`, `code generated`, `do not edit`, etc. - # - `disable`: disable the generated files exclusion. - # - # Default: lax - exclude-generated: strict - # The list of ids of default excludes to include or disable. - # https://golangci-lint.run/usage/false-positives/#default-exclusions - # Default: [] - include: - - EXC0001 - - EXC0002 - - EXC0003 - - EXC0004 - - EXC0005 - - EXC0006 - - EXC0007 - - EXC0008 - - EXC0009 - - EXC0010 - - EXC0011 - - EXC0012 - - EXC0013 - - EXC0014 - - EXC0015 - # Maximum issues count per one linter. - # Set to 0 to disable. - # Default: 50 max-issues-per-linter: 0 - # Maximum count of issues with the same text. - # Set to 0 to disable. - # Default: 3 max-same-issues: 0 - # Show only new issues: if there are unstaged changes or untracked files, - # only those changes are analyzed, else only changes in HEAD~ are analyzed. - # It's a super-useful option for integration of golangci-lint into existing large codebase. - # It's not practical to fix all existing issues at the moment of integration: - # much better don't allow issues in new code. - # - # Default: false - #new: true - # Show only new issues created after git revision `REV`. - # Default: "" - #new-from-rev: HEAD - # Show only new issues created in git patch with set file path. - # Default: "" - #new-from-patch: path/to/patch/file - # Show issues in any part of update files (requires new-from-rev or new-from-patch). - # Default: false - #whole-files: true - # Fix found issues (if it's supported by the linter). - # Default: false - #fix: true severity: - # Set the default severity for issues. - # - # If severity rules are defined and the issues do not match or no severity is provided to the rule - # this will be the default severity applied. - # Severities should match the supported severity names of the selected out format. - # - Code climate: https://docs.codeclimate.com/docs/issues#issue-severity - # - Checkstyle: https://checkstyle.sourceforge.io/property_types.html#SeverityLevel - # - GitHub: https://help.github.com/en/actions/reference/workflow-commands-for-github-actions#setting-an-error-message - # - TeamCity: https://www.jetbrains.com/help/teamcity/service-messages.html#Inspection+Instance - # - # `@linter` can be used as severity value to keep the severity from linters (e.g. revive, gosec, ...) - # - # Default: "" - default-severity: error - # If set to true `severity-rules` regular expressions become case-sensitive. - # Default: false - #case-sensitive: true - # When a list of severity rules are provided, severity information will be added to lint issues. - # Severity rules have the same filtering capability as exclude rules - # except you are allowed to specify one matcher per severity rule. - # - # `@linter` can be used as severity value to keep the severity from linters (e.g. revive, gosec, ...) - # - # Only affects out formats that support setting severity information. - # - # Default: [] + default: error rules: - linters: - dupl severity: info +formatters: + enable: + - gci + - gofmt + - gofumpt + - goimports + exclusions: + paths: + - third_party$ + - builtin$ + - examples$ diff --git a/api/scanner/exif/exif_parser_external.go b/api/scanner/exif/exif_parser_external.go index f4df4ae0..fc222cb9 100644 --- a/api/scanner/exif/exif_parser_external.go +++ b/api/scanner/exif/exif_parser_external.go @@ -1,6 +1,7 @@ package exif import ( + "fmt" "log" "math" "time" @@ -80,9 +81,17 @@ func extractValidGpsData(fileInfo *exiftool.FileMetadata, mediaPath string) (*fl // GPS data validation if (GPSLat != nil && math.Abs(*GPSLat) > 90) || (GPSLong != nil && math.Abs(*GPSLong) > 180) { + latStr := "" + if GPSLat != nil { + latStr = fmt.Sprintf("%f", *GPSLat) + } + longStr := "" + if GPSLong != nil { + longStr = fmt.Sprintf("%f", *GPSLong) + } log.Printf( - "Incorrect GPS data in the %s Exif data: %f, %f, while expected latitude between '-90' and '90', and longitude between '-180' and '180'. Ignoring GPS data.", - mediaPath, *GPSLat, *GPSLong) + "Incorrect GPS data in the %s Exif metadata: %s, %s, (expected latitude '-90'..'90' / longitude '-180'..'180'). Ignoring GPS data.", + mediaPath, latStr, longStr) return nil, nil } return GPSLat, GPSLong diff --git a/api/scanner/exif/exif_parser_internal.go b/api/scanner/exif/exif_parser_internal.go index 4e7c4bf2..fa6a8911 100644 --- a/api/scanner/exif/exif_parser_internal.go +++ b/api/scanner/exif/exif_parser_internal.go @@ -148,7 +148,7 @@ func (p internalExifParser) ParseExif(mediaPath string) (returnExif *models.Medi returnExif = &newExif log.Printf( "Incorrect GPS data in the %s Exif data: %f, %f, while expected latitude between '-90' and '90', and longitude between '-180' and '180'. Ignoring GPS data.", - mediaPath, long, lat) + mediaPath, lat, long) return } else { newExif.GPSLatitude = &lat