Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
50 commits
Select commit Hold shift + click to select a range
9ab36eb
Add service package for interacting with systemd units
jdpleiness Mar 29, 2023
5517bf0
Add disk package for interacting with disks
jdpleiness Mar 30, 2023
a77af7d
Add kernel package for interacting with the kernel
jdpleiness Mar 30, 2023
7de2b80
Add os package for interacting with an operating system
jdpleiness Mar 30, 2023
3a79eed
Add user package for interacting with users
jdpleiness Mar 30, 2023
7498e4c
Add k3s package for interacting with and installing k3s
jdpleiness Mar 31, 2023
6ebe137
Add project files
jdpleiness Mar 31, 2023
6299adf
Add basic skeleton for cmd
jdpleiness Mar 31, 2023
647cbb3
deploy/installer: Add pkg to determine linux distro
jdpleiness May 24, 2023
0726c0a
deploy/installer: Add containerd pkg
jdpleiness May 24, 2023
95100a3
deploy/installer: Add kernel pkg
jdpleiness May 25, 2023
375f749
deploy/installer: Fix error returns
jdpleiness May 25, 2023
15c8022
deploy/installer: Add k3s pkg
jdpleiness May 25, 2023
91b12b0
deploy/installer: Add image pkg
jdpleiness May 25, 2023
bce5044
deploy/installer: Add helm pkg
jdpleiness May 25, 2023
b02da6f
deploy/installer: Fix reference test
jdpleiness May 25, 2023
7e4b828
deploy/installer: Fix unhandled error
jdpleiness May 26, 2023
f6c6e56
deploy/installer: Add sourcegraph pkg
jdpleiness May 26, 2023
a6545dc
deploy/installer: WIP basic CLI install command
jdpleiness May 26, 2023
6f28efc
deploy/installer: Refactor disk pkg
jdpleiness May 31, 2023
2eb4728
deploy/installer: Add functions for k3s and sg install
jdpleiness May 31, 2023
ae94b29
deploy/installer: WIP working installer for AWS
jdpleiness May 31, 2023
afa5e65
Add project wide config
jdpleiness May 31, 2023
a13383c
deploy/installer: Updated docstrings for k3s pkg
jdpleiness May 31, 2023
acb252d
deploy/installer: Update docstrings
jdpleiness May 31, 2023
7dd2624
deploy/installer: Add oneshot for initial setup
jdpleiness May 31, 2023
c3f9536
deploy/installer: Add sourcegraphd WIP
jdpleiness May 31, 2023
773213b
deploy/installer: Refactor pkg naming
jdpleiness May 31, 2023
4ee129e
deploy/installer: Refactor override
jdpleiness May 31, 2023
95d95b5
deploy/installer: Add sourcegraph upgrade
jdpleiness Jun 1, 2023
020d645
deploy/installer: Fix editorconfig issues
jdpleiness Jun 1, 2023
005649e
deploy/installer: Add systemd services to install
jdpleiness Jun 1, 2023
b91242f
deploy/installer: Add check for initial setup
jdpleiness Jun 1, 2023
2f76446
deploy/installer: Add logging to sourcegraphd
jdpleiness Jun 1, 2023
605b2ee
deploy/installer: Remove unsed configs
jdpleiness Jun 1, 2023
cbe11c4
deploy/installer: Add logging to main install
jdpleiness Jun 1, 2023
6631f60
deploy/installer: Fix missed err
jdpleiness Jun 1, 2023
5ecbcd6
deploy/installer: Add packer build configs
jdpleiness Jun 6, 2023
f2a5bdf
deploy/installer: Modify build script to build go binaries
jdpleiness Jun 9, 2023
3e90a75
deploy/installer: Fix issues from PR review
jdpleiness Jun 12, 2023
ee718ba
deploy/installer: Add feature flag to integration style test
jdpleiness Jun 12, 2023
7668bc6
deploy/installer: Add k3s reset for upgrade process
jdpleiness Jun 13, 2023
b17efb6
deploy/installer: Update fix WIP
jdpleiness Jun 15, 2023
5b316ef
Fix imports order
jdpleiness Jul 12, 2023
f424470
Refactor distro pkg
jdpleiness Jul 12, 2023
4537d3e
Run soucegraphd as root
jdpleiness Jul 13, 2023
5dbf031
Add specific kubeconfig to Helm SDK calls
jdpleiness Jul 13, 2023
586cb3d
Add wait for mount to sourcegraphd
jdpleiness Jul 18, 2023
cad1531
Refactor methods around upgrades
jdpleiness Jul 18, 2023
e2cdec3
Refactor error checking statements
jdpleiness Jul 19, 2023
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
7 changes: 7 additions & 0 deletions .editorconfig
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
[*]
insert_final_newline = true
charset = utf-8
trim_trailing_whitespace = true

[{*.sh,*.bash}]
indent_size = 2
3 changes: 3 additions & 0 deletions .gitattributes
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
internal/k3s/bin/k3s filter=lfs diff=lfs merge=lfs -text
internal/k3s/bin/k3s-airgap-images-amd64.tar.gz filter=lfs diff=lfs merge=lfs -text
internal/helm/bin/helm filter=lfs diff=lfs merge=lfs -text
7 changes: 6 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
@@ -1,4 +1,9 @@
.ami-output
.env
*.tar.gz
.DS_Store
.idea
.test-data
.terraform
.terraform.lock.hcl
terraform.tfstate
terraform.tfstate.backup
10 changes: 6 additions & 4 deletions build.sh
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
#!/usr/bin/env bash
set -exuo pipefail

# AWS AMI
packer build --var-file=./packer/build-variables.hcl ./packer/aws/aws-builder.pkr.hcl
# GCE Images
packer build --var-file=./packer/build-variables.hcl ./packer/gcp/gcp-builder.pkr.hcl
version=$1

# Build Go binaries
env GOOS=linux GOARCH=amd64 go build -ldflags "-X main.sgversion=$version" -o cmd/install/bin/sg-init ./cmd/init/
env GOOS=linux GOARCH=amd64 go build -ldflags "-X main.sgversion=$version" -o cmd/install/bin/sourcegraphd ./cmd/sourcegraphd/
env GOOS=linux GOARCH=amd64 go build -ldflags "-X main.sgversion=$version" -o bin/sginstall ./cmd/install/
80 changes: 80 additions & 0 deletions cmd/init/main.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
package main

import (
"context"
"os"

"github.com/rs/zerolog"
"github.com/rs/zerolog/journald"
"github.com/sourcegraph/conc/iter"
"github.com/sourcegraph/deploy/internal/image"
"github.com/sourcegraph/deploy/internal/k3s"
"github.com/sourcegraph/deploy/internal/system/distro"
"github.com/sourcegraph/deploy/internal/system/service"
)

var (
version = "latest"
sgversion = "v5.0.4"
)

func main() {
w := journald.NewJournalDWriter()
logger := zerolog.New(w).With().Caller().Logger()
ctx := context.Background()

if err := run(ctx, &logger); err != nil {
os.Exit(1)
}
}

func run(ctx context.Context, logger *zerolog.Logger) error {
logger.Info().Str("version", version).Str("sgversion", sgversion).Msg("starting sourcegraph init")

err := initialSetup(ctx, logger)
if err != nil {
logger.Error().Err(err).Msg("initial setup failed")
return err
}

return nil
}

func initialSetup(ctx context.Context, logger *zerolog.Logger) error {
logger.Info().Msg("checking k3s.service status")
running, err := service.IsRunning(ctx, "k3s.service")
if err != nil {
logger.Error().Err(err).Msg("failed to get k3s.service status")
return err
}

if !running {
logger.Info().Msg("k3s.service not running, attempting to start k3s.service")
err := service.Start(ctx, "k3s.service")
if err != nil {
logger.Error().Err(err).Msg("failed to start k3s.service")
return err
}
}

if distro.IsAmazonLinux() {
logger.Info().Msg("detected amazon linux")

logger.Info().Msg("starting k3s configuration setup")
err = k3s.Configure("ec2-user")
if err != nil {
logger.Error().Err(err).Msg("failed to configure k3s for user")
return err
}
}

logger.Info().Msg("loading sourcegraph images to containerd")
iter.ForEach(image.Images(), func(img *string) {
err = image.SaveLoad(ctx, *img)
if err != nil {
logger.Error().Err(err).Msgf("failed to load image: %s", *img)
}
})

return nil
}
12 changes: 12 additions & 0 deletions cmd/install/bin/sg-init.service
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
[Unit]
Description=Performs the initial sourcegraph setup setups.
After=network.target

[Service]
Type=oneshot
RemainAfterExit=yes
ExecStart=/usr/local/bin/sg-init
ExecStartPost=/bin/systemctl disable sg-init.service

[Install]
WantedBy=multi-user.target
13 changes: 13 additions & 0 deletions cmd/install/bin/sourcegraphd.service
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
[Unit]
Description=Monitors sourcegraph install and performs updates.
After=network.target
After=sg-init.service
After=mnt-data.mount

[Service]
ExecStart=/usr/local/bin/sourcegraphd
RestartSec=3
KillMode=process

[Install]
WantedBy=multi-user.target
244 changes: 244 additions & 0 deletions cmd/install/install.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,244 @@
package main

import (
"context"
"os"
"os/user"

"github.com/spf13/cobra"

"github.com/sourcegraph/conc/iter"
"github.com/sourcegraph/sourcegraph/lib/errors"

"github.com/sourcegraph/deploy/internal/containerd"
"github.com/sourcegraph/deploy/internal/helm"
"github.com/sourcegraph/deploy/internal/image"
"github.com/sourcegraph/deploy/internal/k3s"
"github.com/sourcegraph/deploy/internal/sourcegraph"
"github.com/sourcegraph/deploy/internal/system/disk"
"github.com/sourcegraph/deploy/internal/system/distro"
"github.com/sourcegraph/deploy/internal/system/kernel"
"github.com/sourcegraph/deploy/internal/system/service"
)

var installCmd = &cobra.Command{
Use: "install",
Short: "installs sourcegraph",
RunE: install,
}

func init() {
rootCmd.AddCommand(installCmd)
}

func install(cmd *cobra.Command, args []string) error {
logger.Info().Str("version", version).Str("sgversion", sgversion).Msg("starting sourcegraph installer")

// make sure we are running as root
logger.Info().Msg("checking current user")
u, err := user.Current()
if err != nil {
logger.Error().Err(err).Msg("could not check current user")
return err
}

if u.Uid != "0" {
logger.Error().Err(err).Msg("current user was not root")
return errors.Errorf("please rerun installer with root privileges")
}

// setup kernel parameters needed for Sourcegraph
logger.Info().Msg("setting kernel parameters")
err = kernel.SetInotifyMaxUserWatches(cmd.Context(), 128_000)
if err != nil {
logger.Error().Err(err).Msg("could not set inotify max user watches")
return err
}

if err := kernel.SetVmMaxMapCount(cmd.Context(), 300_000); err != nil {
logger.Error().Err(err).Msg("could not set vm max map count")
return err
}

if err := kernel.SetSoftNProc(8_192); err != nil {
logger.Error().Err(err).Msg("could not set soft nproc")
return err
}

if err := kernel.SetHardNProc(16_384); err != nil {
logger.Error().Err(err).Msg("could not set hard nproc")
return err
}

if err := kernel.SetSoftNoFile(262_144); err != nil {
logger.Error().Err(err).Msg("could not set soft nfile")
return err
}

if err := kernel.SetHardNoFile(262_144); err != nil {
logger.Error().Err(err).Msg("could not set hard nfile")
return err
}

if distro.IsAmazonLinux() {
logger.Info().Msg("amazon linux detected, check for data volume setup")
mounted, err := disk.IsMounted("/mnt/data", "/dev/nvme1n1")
if err != nil {
logger.Error().Err(err).Msg("could not find data disk")
return err
}

if !mounted {
logger.Info().Msg("no data disk found, setting up data volume")
err := disk.NewDisk(cmd.Context(), "/mnt/data", "/dev/nvme1n1", disk.XFS, disk.Mount())
if err != nil {
logger.Error().Err(err).Msg("could not setup data disk")
return err
}
}
}

logger.Info().Msg("setting up data volume symlinks")
if err = k3s.LinkDataVolumes(); err != nil {
logger.Error().Err(err).Msg("could not setup data volume symlinks")
return err
}

logger.Info().Msg("installing containerd")
if err = containerd.Install(cmd.Context()); err != nil {
logger.Error().Err(err).Msg("could not install containerd")
return err
}

logger.Info().Msg("pulling sourcegraph images")
iter.ForEach(image.Images(), func(img *string) {
if err = image.Pull(cmd.Context(), *img); err != nil {
logger.Error().Err(err).Msgf("could not pull image: %s", *img)
}
})

logger.Info().Msg("installing k3s")
if err = k3s.Install(cmd.Context()); err != nil {
logger.Error().Err(err).Msg("could not install k3s")
return err
}

logger.Info().Msg("installing helm")
if err = helm.Install(); err != nil {
logger.Error().Err(err).Msg("could not install helm")
return err
}

logger.Info().Msg("unpacking k8s configurations")
if err = sourcegraph.UnpackK8sConfigs(); err != nil {
logger.Error().Err(err).Msg("could not unpack k8s configurations")
return err
}

if distro.IsAmazonLinux() {
logger.Info().Msg("writing sourcegraph version files")
if err = sourcegraph.WriteSourcegraphVersion(sgversion, "ec2-user"); err != nil {
logger.Error().Err(err).Msg("could not write sourcegraph version files")
return err
}
}

logger.Info().Msg("setting up sg-init systemd service")
if err = setupSGInit(cmd.Context()); err != nil {
logger.Error().Err(err).Msg("could not setup sg-init systemd service")
return err
}

logger.Info().Msg("setting up sourcegraphd systemd service")
if err = setupSourcegraphd(cmd.Context()); err != nil {
logger.Error().Err(err).Msg("could not setup sourcegraphd systemd service")
return err
}

return nil
}

func setupSGInit(ctx context.Context) error {
srv, err := embeddedFS.ReadFile("bin/sg-init.service")
if err != nil {
return err
}

unpackedSrv, err := os.OpenFile("/etc/systemd/system/sg-init.service", os.O_RDWR|os.O_CREATE, 0754)
if err != nil {
return err
}
defer func() {
_ = unpackedSrv.Close()
}()

_, err = unpackedSrv.Write(srv)
if err != nil {
return err
}

bin, err := embeddedFS.ReadFile("bin/sg-init")
if err != nil {
return err
}

unpackedBin, err := os.OpenFile("/usr/local/bin/sg-init", os.O_RDWR|os.O_CREATE, 0755)
if err != nil {
return err
}
defer func() {
_ = unpackedBin.Close()
}()

_, err = unpackedBin.Write(bin)
if err != nil {
return err
}

if err = service.Enable(ctx, "sg-init.service"); err != nil {
return err
}

return nil
}

func setupSourcegraphd(ctx context.Context) error {
srv, err := embeddedFS.ReadFile("bin/sourcegraphd.service")
if err != nil {
return err
}

unpackedSrv, err := os.OpenFile("/etc/systemd/system/sourcegraphd.service", os.O_RDWR|os.O_CREATE, 0755)
if err != nil {
return err
}

_, err = unpackedSrv.Write(srv)
if err != nil {
return err
}

bin, err := embeddedFS.ReadFile("bin/sourcegraphd")
if err != nil {
return err
}

unpackedBin, err := os.OpenFile("/usr/local/bin/sourcegraphd", os.O_RDWR|os.O_CREATE, 0755)
if err != nil {
return err
}
defer func() {
_ = unpackedBin.Close()
}()

_, err = unpackedBin.Write(bin)
if err != nil {
return err
}

if err = service.Enable(ctx, "sourcegraphd.service"); err != nil {
return nil
}

return nil
}
Loading