diff --git a/.gitignore b/.gitignore
index 8b04583..e2c1618 100644
--- a/.gitignore
+++ b/.gitignore
@@ -126,3 +126,4 @@ fabric.properties
# Android studio 3.1+ serialized cache file
.idea/caches/build_file_checksums.ser
+config.ini
\ No newline at end of file
diff --git a/.gitmodules b/.gitmodules
new file mode 100644
index 0000000..8781b1e
--- /dev/null
+++ b/.gitmodules
@@ -0,0 +1,3 @@
+[submodule "ezconf"]
+ path = ezconf
+ url = https://git.nevets.tech/Steven/ezconf.git
diff --git a/.idea/.gitignore b/.idea/.gitignore
new file mode 100644
index 0000000..13566b8
--- /dev/null
+++ b/.idea/.gitignore
@@ -0,0 +1,8 @@
+# Default ignored files
+/shelf/
+/workspace.xml
+# Editor-based HTTP Client requests
+/httpRequests/
+# Datasource local storage ignored files
+/dataSources/
+/dataSources.local.xml
diff --git a/.idea/.name b/.idea/.name
new file mode 100644
index 0000000..2ec968e
--- /dev/null
+++ b/.idea/.name
@@ -0,0 +1 @@
+SimpleFileSync
\ No newline at end of file
diff --git a/.idea/SimpleFileSync.iml b/.idea/SimpleFileSync.iml
new file mode 100644
index 0000000..5e764c4
--- /dev/null
+++ b/.idea/SimpleFileSync.iml
@@ -0,0 +1,9 @@
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/.idea/modules.xml b/.idea/modules.xml
new file mode 100644
index 0000000..6bbc0ea
--- /dev/null
+++ b/.idea/modules.xml
@@ -0,0 +1,8 @@
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Main.go b/Main.go
new file mode 100644
index 0000000..1f6a634
--- /dev/null
+++ b/Main.go
@@ -0,0 +1,61 @@
+package main
+
+import (
+ "crypto/tls"
+ "fmt"
+ "git.nevets.tech/Steven/ezconf"
+ "github.com/getlantern/systray"
+ "os"
+ "time"
+)
+
+var Config *ezconf.Configuration
+var Connection *tls.Conn
+
+func main() {
+ Config = ezconf.NewConfiguration("./config.ini")
+ Connection = New(Config.GetAsString("General.server"), Config.GetAsInt("General.port"))
+
+ systray.Run(onReady, onExit)
+}
+
+func onReady() {
+ systray.SetIcon(getIcon("assets/icon.ico"))
+ systray.SetTooltip("SimpleFileSync")
+ itemOne := systray.AddMenuItem("Item-1", "Highlighted Item 1")
+ systray.AddSeparator()
+ sync := systray.AddMenuItem("Sync", "Trigger Sync Now")
+ systray.AddSeparator()
+ quit := systray.AddMenuItem("Quit", "Quit")
+
+ go func() {
+ for {
+ select {
+ case <-itemOne.ClickedCh:
+ if itemOne.Checked() {
+ itemOne.Uncheck()
+ } else {
+ itemOne.Check()
+ }
+ case <-sync.ClickedCh:
+ sync.SetTitle("Syncing...")
+ time.Sleep(1000)
+ sync.SetTitle("Last sync at " + time.Now().Format(time.TimeOnly))
+ case <-quit.ClickedCh:
+ systray.Quit()
+ }
+ }
+ }()
+}
+
+func onExit() {
+
+}
+
+func getIcon(location string) []byte {
+ bytes, err := os.ReadFile(location)
+ if err != nil {
+ fmt.Print(err)
+ }
+ return bytes
+}
diff --git a/assets/icon.ico b/assets/icon.ico
new file mode 100644
index 0000000..f8d94fb
Binary files /dev/null and b/assets/icon.ico differ
diff --git a/example-config.ini b/example-config.ini
new file mode 100644
index 0000000..e998b4a
--- /dev/null
+++ b/example-config.ini
@@ -0,0 +1,19 @@
+[General]
+server = sfs.example.com
+port = 7392
+username = user
+auth-token = token
+; http:// or https:// is necessary
+; port is optional
+http-server = http://sfs.example.com:80
+public-key =
+
+[Share]
+sync-interval = 60
+
+
+[Share.example]
+; "anywhere", "non-metered", "local-only"
+sync-location = anywhere
+client-location = C:\Users\sfs\example\
+
diff --git a/ezconf b/ezconf
new file mode 160000
index 0000000..397365d
--- /dev/null
+++ b/ezconf
@@ -0,0 +1 @@
+Subproject commit 397365ddd2fa6359058b7f6dd62eb516387e3994
diff --git a/filetransfer.go b/filetransfer.go
new file mode 100644
index 0000000..06ab7d0
--- /dev/null
+++ b/filetransfer.go
@@ -0,0 +1 @@
+package main
diff --git a/filewatcher.go b/filewatcher.go
new file mode 100644
index 0000000..d65e1fb
--- /dev/null
+++ b/filewatcher.go
@@ -0,0 +1,7 @@
+package main
+
+import "os"
+
+func checkDirectory(path os.File) {
+
+}
diff --git a/go.mod b/go.mod
new file mode 100644
index 0000000..8e5087e
--- /dev/null
+++ b/go.mod
@@ -0,0 +1,24 @@
+module main
+
+go 1.20
+
+replace git.nevets.tech/Steven/ezconf v0.0.0-20230501190348-397365ddd2fa => ./ezconf
+
+require (
+ git.nevets.tech/Steven/ezconf v0.0.0-20230501190348-397365ddd2fa
+ github.com/getlantern/systray v1.2.1
+)
+
+require (
+ github.com/getlantern/context v0.0.0-20190109183933-c447772a6520 // indirect
+ github.com/getlantern/errors v0.0.0-20190325191628-abdb3e3e36f7 // indirect
+ github.com/getlantern/golog v0.0.0-20190830074920-4ef2e798c2d7 // indirect
+ github.com/getlantern/hex v0.0.0-20190417191902-c6586a6fe0b7 // indirect
+ github.com/getlantern/hidden v0.0.0-20190325191715-f02dbb02be55 // indirect
+ github.com/getlantern/ops v0.0.0-20190325191751-d70cb0d6f85f // indirect
+ github.com/go-stack/stack v1.8.0 // indirect
+ github.com/oxtoacart/bpool v0.0.0-20190530202638-03653db5a59c // indirect
+ golang.org/x/sys v0.0.0-20200515095857-1151b9dac4a9 // indirect
+ gopkg.in/ini.v1 v1.67.0 // indirect
+ gopkg.in/yaml.v3 v3.0.1 // indirect
+)
diff --git a/go.sum b/go.sum
new file mode 100644
index 0000000..ee63953
--- /dev/null
+++ b/go.sum
@@ -0,0 +1,32 @@
+github.com/davecgh/go-spew v1.1.0 h1:ZDRjVQ15GmhC3fiQ8ni8+OwkZQO4DARzQgrnXU1Liz8=
+github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
+github.com/getlantern/context v0.0.0-20190109183933-c447772a6520 h1:NRUJuo3v3WGC/g5YiyF790gut6oQr5f3FBI88Wv0dx4=
+github.com/getlantern/context v0.0.0-20190109183933-c447772a6520/go.mod h1:L+mq6/vvYHKjCX2oez0CgEAJmbq1fbb/oNJIWQkBybY=
+github.com/getlantern/errors v0.0.0-20190325191628-abdb3e3e36f7 h1:6uJ+sZ/e03gkbqZ0kUG6mfKoqDb4XMAzMIwlajq19So=
+github.com/getlantern/errors v0.0.0-20190325191628-abdb3e3e36f7/go.mod h1:l+xpFBrCtDLpK9qNjxs+cHU6+BAdlBaxHqikB6Lku3A=
+github.com/getlantern/golog v0.0.0-20190830074920-4ef2e798c2d7 h1:guBYzEaLz0Vfc/jv0czrr2z7qyzTOGC9hiQ0VC+hKjk=
+github.com/getlantern/golog v0.0.0-20190830074920-4ef2e798c2d7/go.mod h1:zx/1xUUeYPy3Pcmet8OSXLbF47l+3y6hIPpyLWoR9oc=
+github.com/getlantern/hex v0.0.0-20190417191902-c6586a6fe0b7 h1:micT5vkcr9tOVk1FiH8SWKID8ultN44Z+yzd2y/Vyb0=
+github.com/getlantern/hex v0.0.0-20190417191902-c6586a6fe0b7/go.mod h1:dD3CgOrwlzca8ed61CsZouQS5h5jIzkK9ZWrTcf0s+o=
+github.com/getlantern/hidden v0.0.0-20190325191715-f02dbb02be55 h1:XYzSdCbkzOC0FDNrgJqGRo8PCMFOBFL9py72DRs7bmc=
+github.com/getlantern/hidden v0.0.0-20190325191715-f02dbb02be55/go.mod h1:6mmzY2kW1TOOrVy+r41Za2MxXM+hhqTtY3oBKd2AgFA=
+github.com/getlantern/ops v0.0.0-20190325191751-d70cb0d6f85f h1:wrYrQttPS8FHIRSlsrcuKazukx/xqO/PpLZzZXsF+EA=
+github.com/getlantern/ops v0.0.0-20190325191751-d70cb0d6f85f/go.mod h1:D5ao98qkA6pxftxoqzibIBBrLSUli+kYnJqrgBf9cIA=
+github.com/getlantern/systray v1.2.1 h1:udsC2k98v2hN359VTFShuQW6GGprRprw6kD6539JikI=
+github.com/getlantern/systray v1.2.1/go.mod h1:AecygODWIsBquJCJFop8MEQcJbWFfw/1yWbVabNgpCM=
+github.com/go-stack/stack v1.8.0 h1:5SgMzNM5HxrEjV0ww2lTmX6E2Izsfxas4+YHWRs3Lsk=
+github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY=
+github.com/oxtoacart/bpool v0.0.0-20190530202638-03653db5a59c h1:rp5dCmg/yLR3mgFuSOe4oEnDDmGLROTvMragMUXpTQw=
+github.com/oxtoacart/bpool v0.0.0-20190530202638-03653db5a59c/go.mod h1:X07ZCGwUbLaax7L0S3Tw4hpejzu63ZrrQiUe6W0hcy0=
+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.8.2 h1:+h33VjcLVPDHtOdpUCuF+7gSuG3yGIftsP1YvFihtJ8=
+golang.org/x/sys v0.0.0-20200515095857-1151b9dac4a9 h1:YTzHMGlqJu67/uEo1lBv0n3wBXhXNeUbB1XfN2vmTm0=
+golang.org/x/sys v0.0.0-20200515095857-1151b9dac4a9/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
+gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
+gopkg.in/ini.v1 v1.67.0 h1:Dgnx+6+nfE+IfzjUEISNeydPJh9AXNNsWbGP9KzCsOA=
+gopkg.in/ini.v1 v1.67.0/go.mod h1:pNLf8WUiyNEtQjuu5G5vTm06TEv9tsIgeAvK8hOrP4k=
+gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
+gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
diff --git a/go.work.sum b/go.work.sum
new file mode 100644
index 0000000..9adf377
--- /dev/null
+++ b/go.work.sum
@@ -0,0 +1,2 @@
+github.com/stretchr/objx v0.5.0 h1:1zr/of2m5FGMsad5YfcqgdqdWrIhu+EBEJRhR1U7z/c=
+gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM=
diff --git a/serverconnection.go b/serverconnection.go
new file mode 100644
index 0000000..6e0a573
--- /dev/null
+++ b/serverconnection.go
@@ -0,0 +1,64 @@
+package main
+
+import (
+ "crypto/tls"
+ "crypto/x509"
+ "fmt"
+ "io"
+ "net/http"
+ "os"
+)
+
+type ClientConn struct {
+ tlsConn *tls.Conn
+ credentials Credentials
+ isAuthed bool
+}
+
+type Credentials struct {
+ user string
+ pass string
+}
+
+func New(host string, port int) *tls.Conn {
+ cert, err := os.ReadFile("./public.pem")
+ if err != nil {
+ fmt.Printf("Error reading cert from ./public.pem: %v", err)
+ os.Exit(1)
+ }
+
+ certPool := x509.NewCertPool()
+ if ok := certPool.AppendCertsFromPEM(cert); !ok {
+ fmt.Printf("Error loading certificate %v into cert pool", cert)
+ os.Exit(1)
+ }
+ config := &tls.Config{RootCAs: certPool}
+ conn, err := tls.Dial("tcp", host+":"+string(rune(port)), config)
+ return conn
+}
+
+func getPublicKey() {
+ out, err := os.Create("./public.pem")
+ if err != nil {
+ fmt.Printf("Error closing file writer: %v", err)
+ os.Exit(1)
+ }
+ defer out.Close()
+
+ resp, err := http.Get(Config.GetAsString("General.http-server") + "/public.pem")
+ if err != nil {
+ fmt.Printf("Error fetching public key: %v", err)
+ os.Exit(1)
+ }
+ defer resp.Body.Close()
+
+ if resp.StatusCode != http.StatusOK {
+ fmt.Printf("Request was unseccessful with code %v", resp.StatusCode)
+ }
+
+ _, err = io.Copy(out, resp.Body)
+ if err != nil {
+ fmt.Printf("Error writing public key to file: %v", err)
+ os.Exit(1)
+ }
+}