Skip to content

Commit

Permalink
Merge branch 'main' into ioutil
Browse files Browse the repository at this point in the history
* main: (32 commits)
  cmd/syncthing: Implement generate as a subcommand with optional API credential setting (fixes syncthing#8021) (syncthing#8043)
  lib/model: Correct "reverting folder" log entry
  lib/model: Correct handling of fakefs cache
  gui, lib: Fix tracking deleted locally-changed on encrypted (fixes syncthing#7715) (syncthing#7726)
  lib/config: Move the bcrypt password hashing to GUIConfiguration (syncthing#8028)
  lib/syncthing: Clean up / refactor LoadOrGenerateCertificate() utility function. (syncthing#8025)
  lib/api: http.Request.BasicAuth instead of custom code (syncthing#8039)
  Normalize CLI options to always use two dashes. (syncthing#8037)
  gui: Display identicons for discovered device IDs. (syncthing#8022)
  cmd/syncthing/cli: indexDumpSize doesn't need a heap (syncthing#8024)
  lib/model: Optimize jobQueue performance and memory use (syncthing#8023)
  lib/model: Limit the number of default hashers on Android (ref syncthing#2220)
  lib/model: Set mod. time after writing trailer in shortcut (ref syncthing#7992)
  lib/protocol: Simplify codeToError, errorToCode
  lib/protocol: Eliminate nativeModel on Unix
  gui: Add direct link to Ignore Patterns from folder panel (fixes syncthing#4293) (syncthing#7993)
  gui: Translate theme names in settings (syncthing#8006)
  lib/model: Pull when a new connection is established (fixes syncthing#8012) (syncthing#8013)
  gui, man, authors: Update docs, translations, and contributors
  gui, man, authors: Update docs, translations, and contributors
  ...
  • Loading branch information
calmh committed Nov 22, 2021
2 parents 9dd1712 + 100870e commit d1a36c2
Show file tree
Hide file tree
Showing 96 changed files with 1,399 additions and 651 deletions.
1 change: 1 addition & 0 deletions AUTHORS
Expand Up @@ -182,6 +182,7 @@ Matt Burke (burkemw3) <mburke@amplify.com> <burkemw3@gmail.com>
Matt Robenolt <matt@ydekproductions.com>
Matteo Ruina <matteo.ruina@gmail.com>
Maurizio Tomasi <ziotom78@gmail.com>
Max <github@germancoding.com>
Max Schulze (kralo) <max.schulze@online.de> <kralo@users.noreply.github.com>
MaximAL <almaximal@ya.ru>
Maxime Thirouin <m@moox.io>
Expand Down
4 changes: 2 additions & 2 deletions build.go
Expand Up @@ -142,7 +142,7 @@ var targets = map[string]target{
{src: "LICENSE", dst: "LICENSE.txt", perm: 0644},
{src: "AUTHORS", dst: "AUTHORS.txt", perm: 0644},
},
systemdService: "cmd/stdiscosrv/etc/linux-systemd/stdiscosrv.service",
systemdService: "stdiscosrv.service",
installationFiles: []archiveFile{
{src: "{{binary}}", dst: "deb/usr/bin/{{binary}}", perm: 0755},
{src: "cmd/stdiscosrv/README.md", dst: "deb/usr/share/doc/syncthing-discosrv/README.txt", perm: 0644},
Expand Down Expand Up @@ -170,7 +170,7 @@ var targets = map[string]target{
{src: "LICENSE", dst: "LICENSE.txt", perm: 0644},
{src: "AUTHORS", dst: "AUTHORS.txt", perm: 0644},
},
systemdService: "cmd/strelaysrv/etc/linux-systemd/strelaysrv.service",
systemdService: "strelaysrv.service",
installationFiles: []archiveFile{
{src: "{{binary}}", dst: "deb/usr/bin/{{binary}}", perm: 0755},
{src: "cmd/strelaysrv/README.md", dst: "deb/usr/share/doc/syncthing-relaysrv/README.txt", perm: 0644},
Expand Down
46 changes: 15 additions & 31 deletions cmd/syncthing/cli/index_dumpsize.go
Expand Up @@ -7,53 +7,35 @@
package cli

import (
"container/heap"
"encoding/binary"
"fmt"
"sort"

"github.com/urfave/cli"

"github.com/syncthing/syncthing/lib/db"
)

type SizedElement struct {
key string
size int
}

type ElementHeap []SizedElement

func (h ElementHeap) Len() int { return len(h) }
func (h ElementHeap) Less(i, j int) bool { return h[i].size > h[j].size }
func (h ElementHeap) Swap(i, j int) { h[i], h[j] = h[j], h[i] }

func (h *ElementHeap) Push(x interface{}) {
*h = append(*h, x.(SizedElement))
}

func (h *ElementHeap) Pop() interface{} {
old := *h
n := len(old)
x := old[n-1]
*h = old[0 : n-1]
return x
}

func indexDumpSize(*cli.Context) error {
type sizedElement struct {
key string
size int
}

ldb, err := getDB()
if err != nil {
return err
}

h := &ElementHeap{}
heap.Init(h)

it, err := ldb.NewPrefixIterator(nil)
if err != nil {
return err
}
var ele SizedElement

var elems []sizedElement
for it.Next() {
var ele sizedElement

key := it.Key()
switch key[0] {
case db.KeyTypeDevice:
Expand Down Expand Up @@ -94,11 +76,13 @@ func indexDumpSize(*cli.Context) error {
ele.key = fmt.Sprintf("UNKNOWN:%x", key)
}
ele.size = len(it.Value())
heap.Push(h, ele)
elems = append(elems, ele)
}

for h.Len() > 0 {
ele = heap.Pop(h).(SizedElement)
sort.Slice(elems, func(i, j int) bool {
return elems[i].size > elems[j].size
})
for _, ele := range elems {
fmt.Println(ele.key, ele.size)
}

Expand Down
18 changes: 9 additions & 9 deletions cmd/syncthing/cli/main.go
Expand Up @@ -61,23 +61,23 @@ func Run() error {
fakeFlags := []cli.Flag{
cli.StringFlag{
Name: "gui-address",
Value: "URL",
Usage: "Override GUI address (e.g. \"http://192.0.2.42:8443\")",
Usage: "Override GUI address to `URL` (e.g. \"http://192.0.2.42:8443\")",
},
cli.StringFlag{
Name: "gui-apikey",
Value: "API-KEY",
Usage: "Override GUI API key",
Usage: "Override GUI API key to `API-KEY`",
},
cli.StringFlag{
Name: "home",
Value: "PATH",
Usage: "Set configuration and data directory",
Usage: "Set configuration and data directory to `PATH`",
},
cli.StringFlag{
Name: "conf",
Value: "PATH",
Usage: "Set configuration directory (config and keys)",
Name: "config",
Usage: "Set configuration directory (config and keys) to `PATH`",
},
cli.StringFlag{
Name: "data",
Usage: "Set data directory (database and logs) to `PATH`",
},
}

Expand Down
15 changes: 15 additions & 0 deletions cmd/syncthing/cmdutil/options_common.go
@@ -0,0 +1,15 @@
// Copyright (C) 2021 The Syncthing Authors.
//
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this file,
// You can obtain one at https://mozilla.org/MPL/2.0/.

package cmdutil

// CommonOptions are reused among several subcommands
type CommonOptions struct {
buildCommonOptions
ConfDir string `name:"config" placeholder:"PATH" help:"Set configuration directory (config and keys)"`
HomeDir string `name:"home" placeholder:"PATH" help:"Set configuration and data directory"`
NoDefaultFolder bool `env:"STNODEFAULTFOLDER" help:"Don't create the \"default\" folder on first startup"`
}
Expand Up @@ -7,8 +7,8 @@
//go:build !windows
// +build !windows

package main
package cmdutil

type buildServeOptions struct {
type buildCommonOptions struct {
HideConsole bool `hidden:""`
}
Expand Up @@ -4,8 +4,8 @@
// License, v. 2.0. If a copy of the MPL was not distributed with this file,
// You can obtain one at https://mozilla.org/MPL/2.0/.

package main
package cmdutil

type buildServeOptions struct {
type buildCommonOptions struct {
HideConsole bool `name:"no-console" help:"Hide console window"`
}
4 changes: 2 additions & 2 deletions cmd/syncthing/cmdutil/util.go
Expand Up @@ -18,9 +18,9 @@ func SetConfigDataLocationsFromFlags(homeDir, confDir, dataDir string) error {
dataSet := dataDir != ""
switch {
case dataSet != confSet:
return errors.New("either both or none of -conf and -data must be given, use -home to set both at once")
return errors.New("either both or none of --config and --data must be given, use --home to set both at once")
case homeSet && dataSet:
return errors.New("-home must not be used together with -conf and -data")
return errors.New("--home must not be used together with --config and --data")
case homeSet:
confDir = homeDir
dataDir = homeDir
Expand Down
2 changes: 1 addition & 1 deletion cmd/syncthing/decrypt/decrypt.go
Expand Up @@ -45,7 +45,7 @@ func (c *CLI) Run() error {
log.SetFlags(0)

if c.To == "" && !c.VerifyOnly {
return fmt.Errorf("must set --to or --verify")
return fmt.Errorf("must set --to or --verify-only")
}

if c.TokenPath == "" {
Expand Down
144 changes: 144 additions & 0 deletions cmd/syncthing/generate/generate.go
@@ -0,0 +1,144 @@
// Copyright (C) 2021 The Syncthing Authors.
//
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this file,
// You can obtain one at https://mozilla.org/MPL/2.0/.

// Package generate implements the `syncthing generate` subcommand.
package generate

import (
"bufio"
"context"
"crypto/tls"
"fmt"
"log"
"os"

"github.com/syncthing/syncthing/cmd/syncthing/cmdutil"
"github.com/syncthing/syncthing/lib/config"
"github.com/syncthing/syncthing/lib/events"
"github.com/syncthing/syncthing/lib/fs"
"github.com/syncthing/syncthing/lib/locations"
"github.com/syncthing/syncthing/lib/osutil"
"github.com/syncthing/syncthing/lib/protocol"
"github.com/syncthing/syncthing/lib/syncthing"
)

type CLI struct {
cmdutil.CommonOptions
GUIUser string `placeholder:"STRING" help:"Specify new GUI authentication user name"`
GUIPassword string `placeholder:"STRING" help:"Specify new GUI authentication password (use - to read from standard input)"`
}

func (c *CLI) Run() error {
log.SetFlags(0)

if c.HideConsole {
osutil.HideConsole()
}

if c.HomeDir != "" {
if c.ConfDir != "" {
return fmt.Errorf("--home must not be used together with --config")
}
c.ConfDir = c.HomeDir
}
if c.ConfDir == "" {
c.ConfDir = locations.GetBaseDir(locations.ConfigBaseDir)
}

// Support reading the password from a pipe or similar
if c.GUIPassword == "-" {
reader := bufio.NewReader(os.Stdin)
password, _, err := reader.ReadLine()
if err != nil {
return fmt.Errorf("Failed reading GUI password: %w", err)
}
c.GUIPassword = string(password)
}

if err := Generate(c.ConfDir, c.GUIUser, c.GUIPassword, c.NoDefaultFolder); err != nil {
return fmt.Errorf("Failed to generate config and keys: %w", err)
}
return nil
}

func Generate(confDir, guiUser, guiPassword string, noDefaultFolder bool) error {
dir, err := fs.ExpandTilde(confDir)
if err != nil {
return err
}

if err := syncthing.EnsureDir(dir, 0700); err != nil {
return err
}
locations.SetBaseDir(locations.ConfigBaseDir, dir)

var myID protocol.DeviceID
certFile, keyFile := locations.Get(locations.CertFile), locations.Get(locations.KeyFile)
cert, err := tls.LoadX509KeyPair(certFile, keyFile)
if err == nil {
log.Println("WARNING: Key exists; will not overwrite.")
} else {
cert, err = syncthing.GenerateCertificate(certFile, keyFile)
if err != nil {
return fmt.Errorf("create certificate: %w", err)
}
}
myID = protocol.NewDeviceID(cert.Certificate[0])
log.Println("Device ID:", myID)

cfgFile := locations.Get(locations.ConfigFile)
var cfg config.Wrapper
if _, err := os.Stat(cfgFile); err == nil {
if guiUser == "" && guiPassword == "" {
log.Println("WARNING: Config exists; will not overwrite.")
return nil
}

if cfg, _, err = config.Load(cfgFile, myID, events.NoopLogger); err != nil {
return fmt.Errorf("load config: %w", err)
}
} else {
if cfg, err = syncthing.DefaultConfig(cfgFile, myID, events.NoopLogger, noDefaultFolder); err != nil {
return fmt.Errorf("create config: %w", err)
}
}

ctx, cancel := context.WithCancel(context.Background())
go cfg.Serve(ctx)
defer cancel()

var updateErr error
waiter, err := cfg.Modify(func(cfg *config.Configuration) {
updateErr = updateGUIAuthentication(&cfg.GUI, guiUser, guiPassword)
})
if err != nil {
return fmt.Errorf("modify config: %w", err)
}

waiter.Wait()
if updateErr != nil {
return updateErr
}
if err := cfg.Save(); err != nil {
return fmt.Errorf("save config: %w", err)
}
return nil
}

func updateGUIAuthentication(guiCfg *config.GUIConfiguration, guiUser, guiPassword string) error {
if guiUser != "" && guiCfg.User != guiUser {
guiCfg.User = guiUser
log.Println("Updated GUI authentication user name:", guiUser)
}

if guiPassword != "" && guiCfg.Password != guiPassword {
if err := guiCfg.HashAndSetPassword(guiPassword); err != nil {
return fmt.Errorf("Failed to set GUI authentication password: %w", err)
}
log.Println("Updated GUI authentication password.")
}
return nil
}

0 comments on commit d1a36c2

Please sign in to comment.