Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Import location data #21

Open
wants to merge 15 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,5 @@
tmp*
tools
dedupe/bin/*
*.exe
*.exe
data/*
31 changes: 16 additions & 15 deletions dupes/lib/producerConsumer/main_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import (

"github.com/sander-skjulsvik/tools/dupes/lib/common"
"github.com/sander-skjulsvik/tools/dupes/lib/test"
"github.com/sander-skjulsvik/tools/libs/files"
"github.com/sander-skjulsvik/tools/libs/progressbar"
"gotest.tools/assert"
)
Expand All @@ -36,7 +37,7 @@ func TestGetFiles(t *testing.T) {
workDir + "folder/" + "folder/" + "nesting_file_name",
}
for _, file := range expectedFilePaths {
test.CreateFile(file, "nesting_file_content")
files.CreateFile(file, "nesting_file_content")
}
calculatedFilePaths := make(chan string)
go getFiles(workDir, calculatedFilePaths)
Expand All @@ -59,8 +60,8 @@ func TestGetFiles(t *testing.T) {
{
workDir := baseDir + "test_emtpy_file/"
os.MkdirAll(filepath.Clean(workDir), 0o755)
test.CreateEmptyFile(workDir + "empty_file")
test.CreateFile(workDir+"not_empty_file", "not_empty_file")
files.CreateEmptyFile(workDir + "empty_file")
files.CreateFile(workDir+"not_empty_file", "not_empty_file")

calculatedFilePaths := make(chan string)
go getFiles(workDir, calculatedFilePaths)
Expand All @@ -77,7 +78,7 @@ func TestGetFiles(t *testing.T) {
{
workDir := baseDir + "test_symlink/"
os.MkdirAll(filepath.Clean(workDir), 0o755)
test.CreateEmptyFile(workDir + "source_file")
files.CreateEmptyFile(workDir + "source_file")
os.Symlink(workDir+"source_file", workDir+"destination_file")

calculatedFilePaths := make(chan string)
Expand Down Expand Up @@ -107,9 +108,9 @@ func TestGetFiles(t *testing.T) {
{
workDir := baseDir + "sleeping_before_consuming/"
os.MkdirAll(filepath.Clean(workDir), 0o755)
test.CreateFile(filepath.Join(workDir, "1"), "1")
test.CreateFile(filepath.Join(workDir, "2"), "2")
test.CreateFile(filepath.Join(workDir, "3"), "3")
files.CreateFile(filepath.Join(workDir, "1"), "1")
files.CreateFile(filepath.Join(workDir, "2"), "2")
files.CreateFile(filepath.Join(workDir, "3"), "3")

calculatedFilePathsChan := make(chan string)
calculatedFilePathsSlice := []string{}
Expand All @@ -135,7 +136,7 @@ func TestAppendFileTreadSafe(t *testing.T) {

path := workDir + "single_file"
lock := sync.Mutex{}
test.CreateFile(path, "I am a single file")
files.CreateFile(path, "I am a single file")
expectedHash := "1be3d7cfb6df7ff4ed6235a70603dc3ee8fa636a5e44a5c2ea8ffbcd38b41bd0"

appendFileTreadSafe(&d, filepath.Clean(path), &lock)
Expand Down Expand Up @@ -165,7 +166,7 @@ func TestAppendFileTreadSafe(t *testing.T) {
d := common.NewDupes()
n := 1000
for i := 0; i < n; i++ {
test.CreateFile(workDir+strconv.Itoa(i), "I am one of many files")
files.CreateFile(workDir+strconv.Itoa(i), "I am one of many files")
}

lock := sync.Mutex{}
Expand Down Expand Up @@ -203,7 +204,7 @@ func TestAppendFileTreadSafe(t *testing.T) {
d := common.NewDupes()
n := 1000
for i := 0; i < n; i++ {
test.CreateFile(workDir+strconv.Itoa(i), "I am one of many files: "+strconv.Itoa(i))
files.CreateFile(workDir+strconv.Itoa(i), "I am one of many files: "+strconv.Itoa(i))
}

lock := sync.Mutex{}
Expand Down Expand Up @@ -235,7 +236,7 @@ func TestAppendFileTreadSafe(t *testing.T) {
lock := sync.Mutex{}
n := 10
for i := 0; i < n; i++ {
test.CreateFile(workDir+strconv.Itoa(i), "")
files.CreateFile(workDir+strconv.Itoa(i), "")
}
expectedHash := "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"

Expand Down Expand Up @@ -268,7 +269,7 @@ func TestProcessFiles(t *testing.T) {
os.MkdirAll(filepath.Clean(workDir), 0o755)
path := workDir + "single_file"

test.CreateFile(path, "I am a single file")
files.CreateFile(path, "I am a single file")
expectedHash := "1be3d7cfb6df7ff4ed6235a70603dc3ee8fa636a5e44a5c2ea8ffbcd38b41bd0"

filePaths := make(chan string)
Expand Down Expand Up @@ -324,7 +325,7 @@ func TestProcessFiles(t *testing.T) {
Content: "I am not unique",
}}
for _, file := range expectedFilePaths {
test.CreateFile(file.Path, file.Content)
files.CreateFile(file.Path, file.Content)
}

filePaths := make(chan string)
Expand Down Expand Up @@ -383,7 +384,7 @@ func TestProcessFilesNConsumers(t *testing.T) {
os.MkdirAll(filepath.Clean(workDir), 0o755)
path := workDir + "single_file"

test.CreateFile(path, "I am a single file")
files.CreateFile(path, "I am a single file")
expectedHash := "1be3d7cfb6df7ff4ed6235a70603dc3ee8fa636a5e44a5c2ea8ffbcd38b41bd0"

filePaths := make(chan string)
Expand Down Expand Up @@ -441,7 +442,7 @@ func TestProcessFilesNConsumers(t *testing.T) {
Content: "I am not unique",
}}
for _, file := range expectedFilePaths {
test.CreateFile(file.Path, file.Content)
files.CreateFile(file.Path, file.Content)
}

filePaths := make(chan string)
Expand Down
4 changes: 3 additions & 1 deletion dupes/lib/test/files.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@ import (
"os"
"path/filepath"
"slices"

files "github.com/sander-skjulsvik/tools/libs/files"
)

type Folder struct {
Expand All @@ -28,7 +30,7 @@ func (folder *Folder) Generate(parents string) {
// Create files in the folder
for _, file := range folder.Files {
filePath := filepath.Join(parents, folder.Name, file.Name)
CreateFile(filePath, file.Content)
files.CreateFile(filePath, file.Content)
}

// Create child folders
Expand Down
3 changes: 2 additions & 1 deletion dupes/lib/test/lib.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import (
"path/filepath"

"github.com/sander-skjulsvik/tools/dupes/lib/common"
files "github.com/sander-skjulsvik/tools/libs/files"
)

func SetupExpectedDupes(path string) {
Expand All @@ -17,7 +18,7 @@ func SetupExpectedDupes(path string) {
// Create the parent folders if they don't exist
CrateParentFolders(fullPath)
// Create the file with content from ExpectedDupesHashMap
CreateFile(fullPath, ExpectedDupesHashMap[hash])
files.CreateFile(fullPath, ExpectedDupesHashMap[hash])
}
}
}
Expand Down
9 changes: 0 additions & 9 deletions dupes/lib/test/run.go
Original file line number Diff line number Diff line change
Expand Up @@ -118,12 +118,3 @@ func check(e error) {
panic(e)
}
}

func CreateEmptyFile(path string) {
d := []byte("")
check(os.WriteFile(filepath.Clean(path), d, 0o644))
}

func CreateFile(path, content string) {
check(os.WriteFile(filepath.Clean(path), []byte(content), 0o644))
}
11 changes: 10 additions & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,26 @@ module github.com/sander-skjulsvik/tools

go 1.22

require github.com/gosuri/uiprogress v0.0.1
require (
github.com/adrianmo/go-nmea v1.10.0
github.com/gosuri/uiprogress v0.0.1
)

require (
github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5 // indirect
github.com/google/go-cmp v0.6.0 // indirect
github.com/gosuri/uilive v0.0.4 // indirect
github.com/kylelemons/go-gypsy v1.0.0 // indirect
github.com/lib/pq v1.10.9 // indirect
github.com/mattn/go-isatty v0.0.20 // indirect
github.com/pkg/errors v0.9.1 // indirect
github.com/ziutek/mymysql v1.5.4 // indirect
)

require (
github.com/barasher/go-exiftool v1.10.0
github.com/deckarep/golang-set/v2 v2.6.0
github.com/kellydunn/golang-geo v0.7.0
golang.org/x/sys v0.19.0 // indirect
gotest.tools v2.2.0+incompatible
)
26 changes: 26 additions & 0 deletions go.sum
Original file line number Diff line number Diff line change
@@ -1,17 +1,43 @@
github.com/adrianmo/go-nmea v1.10.0 h1:L1aYaebZ4cXFCoXNSeDeQa0tApvSKvIbqMsK+iaRiCo=
github.com/adrianmo/go-nmea v1.10.0/go.mod h1:u8bPnpKt/D/5rll/5l9f6iDfeq5WZW0+/SXdkwix6Tg=
github.com/barasher/go-exiftool v1.10.0 h1:f5JY5jc42M7tzR6tbL9508S2IXdIcG9QyieEXNMpIhs=
github.com/barasher/go-exiftool v1.10.0/go.mod h1:F9s/a3uHSM8YniVfwF+sbQUtP8Gmh9nyzigNF+8vsWo=
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/deckarep/golang-set/v2 v2.6.0 h1:XfcQbWM1LlMB8BsJ8N9vW5ehnnPVIw0je80NsVHagjM=
github.com/deckarep/golang-set/v2 v2.6.0/go.mod h1:VAky9rY/yGXJOLEDv3OMci+7wtDpOF4IN+y82NBOac4=
github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5 h1:Yzb9+7DPaBjB8zlTR87/ElzFsnQfuHnVUVqpZZIcV5Y=
github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5/go.mod h1:a2zkGnVExMxdzMo3M0Hi/3sEU+cWnZpSni0O6/Yb/P0=
github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI=
github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY=
github.com/gosuri/uilive v0.0.4 h1:hUEBpQDj8D8jXgtCdBu7sWsy5sbW/5GhuO8KBwJ2jyY=
github.com/gosuri/uilive v0.0.4/go.mod h1:V/epo5LjjlDE5RJUcqx8dbw+zc93y5Ya3yg8tfZ74VI=
github.com/gosuri/uiprogress v0.0.1 h1:0kpv/XY/qTmFWl/SkaJykZXrBBzwwadmW8fRb7RJSxw=
github.com/gosuri/uiprogress v0.0.1/go.mod h1:C1RTYn4Sc7iEyf6j8ft5dyoZ4212h8G1ol9QQluh5+0=
github.com/kellydunn/golang-geo v0.7.0 h1:A5j0/BvNgGwY6Yb6inXQxzYwlPHc6WVZR+MrarZYNNg=
github.com/kellydunn/golang-geo v0.7.0/go.mod h1:YYlQPJ+DPEzrHx8kT3oPHC/NjyvCCXE+IuKGKdrjrcU=
github.com/kylelemons/go-gypsy v1.0.0 h1:7/wQ7A3UL1bnqRMnZ6T8cwCOArfZCxFmb1iTxaOOo1s=
github.com/kylelemons/go-gypsy v1.0.0/go.mod h1:chkXM0zjdpXOiqkCW1XcCHDfjfk14PH2KKkQWxfJUcU=
github.com/lib/pq v1.10.9 h1:YXG7RB+JIjhP29X+OtkiDnYaXQwpS4JEWq7dtCCRUEw=
github.com/lib/pq v1.10.9/go.mod h1:AlVN5x4E4T544tWzH6hKfbfQvm3HdbOxrmggDNAPY9o=
github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY=
github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y=
github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4=
github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
github.com/stretchr/testify v1.5.1 h1:nOGnQDM7FYENwehXlg/kFVnos3rEvtKTjRvOWSzb6H4=
github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA=
github.com/ziutek/mymysql v1.5.4 h1:GB0qdRGsTwQSBVYuVShFBKaXSnSnYYC2d9knnE1LHFs=
github.com/ziutek/mymysql v1.5.4/go.mod h1:LMSpPZ6DbqWFxNCHW77HeMg9I646SAhApZ/wKdgO/C0=
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.19.0 h1:q5f1RH2jigJ1MoAWp2KTp3gm5zAGFUTarQZ5U386+4o=
golang.org/x/sys v0.19.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/yaml.v2 v2.2.2 h1:ZCJp+EgiOT7lHqUV2J862kp8Qj64Jo6az82+3Td9dZw=
gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
gotest.tools v2.2.0+incompatible h1:VsBPFP1AI068pPrMxtb/S8Zkgf9xEmTLJjfM+P5UIEo=
gotest.tools v2.2.0+incompatible/go.mod h1:DsYFclhRJ6vuDpmuTbkuFWG+y2sxOXAzmJt81HFBacw=
69 changes: 69 additions & 0 deletions google_location_data/lib/coordinates.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
package lib

import (
"errors"
"fmt"

nmea "github.com/adrianmo/go-nmea"
geo "github.com/kellydunn/golang-geo"
)

type Corrdinates struct {
geo.Point
}

func NewCorrdinatesE2(lat, long float64) Corrdinates {
return Corrdinates{
Point: *geo.NewPoint(lat, long),
}
}

func NewCorrdinatesE7(lat, long int) Corrdinates {
return Corrdinates{
Point: *geo.NewPoint(float64(lat)/1e7, float64(long)/1e7),
}
}

func NewCoordinatesFromGeopoint(point geo.Point) Corrdinates {
return Corrdinates{
Point: point,
}
}

var ErrInvalidDMS = errors.New("Invalid DMS")

func NewCoordinatesFromDMS(latitude, longitude string) (Corrdinates, error) {
lat, err := nmea.ParseDMS(latitude)
if err != nil {
return Corrdinates{}, errors.Join(
ErrInvalidDMS,
fmt.Errorf("latitude: %s", latitude),
err,
)
}
lng, err := nmea.ParseDMS(longitude)
if err != nil {
return Corrdinates{}, errors.Join(
ErrInvalidDMS,
fmt.Errorf("longitude: %s", longitude),
err,
)
}
return NewCorrdinatesE2(lat, lng), nil
}

func (coordinate *Corrdinates) GetE2Coord() (lat float64, long float64) {
return coordinate.Lat(), coordinate.Lng()
}

func (coordinate *Corrdinates) GetE7Coord() (lat int, long int) {
return int(coordinate.Lat() * 1e7), int(coordinate.Lng() * 1e7)
}

func (coordinate *Corrdinates) LatE7() int {
return int(coordinate.Point.Lat() * 1e7)
}

func (coordinate *Corrdinates) LngE7() int {
return int(coordinate.Point.Lng() * 1e7)
}
52 changes: 52 additions & 0 deletions google_location_data/lib/lib.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
package lib

import (
"errors"
"time"

geo "github.com/kellydunn/golang-geo"
)

/*
This function will have to do some assumtions when the time between location stamps is too large.

It is implemented with 3 types of assumptions:

- If the time between the photo and the location is low we will assume it is accurate.
- If the time between the photo and the location is medium we will assume we will attempt a linear interpolation between the two locations.
- If the time is large we will return an error, and assume the user will have to provide the data themselves.
*/

const (
LOW_TIME_DIFF_THRESHOLD = 30 * time.Minute
MEDIUM_TIME_DIFF_THRESHOLD = 2 * time.Hour
HIGH_TIME_DIFF_THRESHOLD = 12 * time.Hour
)

var (
ErrTimeDiffTooHigh = errors.New("Time difference too high")
ErrTimeDiffMedium = errors.New("Time difference medium")
ErrNoLocation = errors.New("No location found")
)

func interpolation(loc1, loc2 LocationRecord, time time.Time) Corrdinates {
// Calculate the ratio of the time difference
timeRatio := timeRatio(loc1.Time, loc2.Time, time)
// Normalized ratio
loc1LatitudeE2, loc1LongitudeE2 := loc1.Corrdinates.GetE2Coord()
loc2LatitudeE2, loc2LongitudeE2 := loc2.Corrdinates.GetE2Coord()

p1 := geo.NewPoint(loc1LatitudeE2, loc1LongitudeE2)
p2 := geo.NewPoint(loc2LatitudeE2, loc2LongitudeE2)

bearing := p1.BearingTo(p2)
distance := p1.GreatCircleDistance(p2)

p3 := p1.PointAtDistanceAndBearing(distance*timeRatio, bearing)

return NewCoordinatesFromGeopoint(*p3)
}

func timeRatio(time1, time2, time time.Time) float64 {
return time.Sub(time1).Seconds() / time2.Sub(time1).Seconds()
}
Loading