2018-09-12 19:16:08 -04:00
|
|
|
package classic
|
|
|
|
|
|
|
|
import (
|
2018-10-24 17:40:32 -04:00
|
|
|
"fmt"
|
|
|
|
|
2018-09-12 19:16:08 -04:00
|
|
|
"github.com/hashicorp/packer/packer"
|
|
|
|
"github.com/hashicorp/packer/template/interpolate"
|
|
|
|
)
|
|
|
|
|
2018-10-24 17:40:32 -04:00
|
|
|
const imageListDefault = "/oracle/public/OL_7.2_UEKR4_x86_64"
|
|
|
|
|
2018-09-12 19:16:08 -04:00
|
|
|
type PVConfig struct {
|
|
|
|
// PersistentVolumeSize lets us control the volume size by using persistent boot storage
|
2018-09-12 20:12:35 -04:00
|
|
|
PersistentVolumeSize int `mapstructure:"persistent_volume_size"`
|
|
|
|
BuilderUploadImageCommand string `mapstructure:"builder_upload_image_command"`
|
2018-10-24 17:40:32 -04:00
|
|
|
|
|
|
|
// Builder Image
|
|
|
|
BuilderShape string `mapstructure:"builder_shape"`
|
|
|
|
BuilderImageList string `mapstructure:"builder_image_list"`
|
|
|
|
BuilderImageListEntry int `mapstructure:"builder_image_list_entry"`
|
2018-09-12 19:16:08 -04:00
|
|
|
/* TODO:
|
|
|
|
some way to choose which connection to use for master
|
|
|
|
possible ignore everything for builder and always use SSH keys
|
2018-10-24 17:49:09 -04:00
|
|
|
* Documentation
|
|
|
|
* Configuration (master/builder images & entry, destination stuff, etc)
|
|
|
|
* Image entry for both master/builder
|
|
|
|
https://github.com/hashicorp/packer/issues/6833
|
|
|
|
* split master/builder image/connection config. i.e. build anything, master only linux
|
2018-09-12 19:16:08 -04:00
|
|
|
*/
|
|
|
|
}
|
|
|
|
|
2018-10-20 17:11:11 -04:00
|
|
|
// IsPV tells us if we're using a persistent volume for this build
|
2018-09-12 20:12:35 -04:00
|
|
|
func (c *PVConfig) IsPV() bool {
|
|
|
|
return c.PersistentVolumeSize > 0
|
|
|
|
}
|
|
|
|
|
2018-09-12 19:16:08 -04:00
|
|
|
func (c *PVConfig) Prepare(ctx *interpolate.Context) (errs *packer.MultiError) {
|
2018-09-12 20:12:35 -04:00
|
|
|
if !c.IsPV() {
|
2018-10-24 17:40:32 -04:00
|
|
|
if c.BuilderShape != "" {
|
|
|
|
errs = packer.MultiErrorAppend(errs,
|
|
|
|
fmt.Errorf("`builder_shape` has no meaning when `persistent_volume_size` is not set."))
|
|
|
|
}
|
|
|
|
if c.BuilderImageList != "" {
|
|
|
|
errs = packer.MultiErrorAppend(errs,
|
|
|
|
fmt.Errorf("`builder_shape_image_list` has no meaning when `persistent_volume_size` is not set."))
|
|
|
|
}
|
|
|
|
return errs
|
|
|
|
}
|
|
|
|
|
|
|
|
if c.BuilderShape == "" {
|
|
|
|
c.BuilderShape = "oc3"
|
|
|
|
}
|
|
|
|
|
|
|
|
if c.BuilderImageList == "" {
|
|
|
|
c.BuilderImageList = imageListDefault
|
|
|
|
}
|
|
|
|
|
|
|
|
// Entry 5 is a working default, so let's set it if the entry is unset and
|
|
|
|
// we're using the default image list
|
|
|
|
if c.BuilderImageList == imageListDefault && c.BuilderImageListEntry == 0 {
|
|
|
|
c.BuilderImageListEntry = 5
|
2018-09-12 19:16:08 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
if c.BuilderUploadImageCommand == "" {
|
2018-10-18 01:21:22 -04:00
|
|
|
c.BuilderUploadImageCommand = `
|
|
|
|
# https://www.oracle.com/webfolder/technetwork/tutorials/obe/cloud/objectstorage/upload_files_gt_5GB_REST_API/upload_files_gt_5GB_REST_API.html
|
2018-10-17 23:16:23 -04:00
|
|
|
|
2018-10-18 01:21:22 -04:00
|
|
|
# Split diskimage in to 100mb chunks
|
|
|
|
split -b 100m diskimage.tar.gz segment_
|
|
|
|
|
2018-10-18 03:39:41 -04:00
|
|
|
# Download jq tool
|
|
|
|
curl -OL https://github.com/stedolan/jq/releases/download/jq-1.5/jq-linux64
|
|
|
|
mv jq-linux64 jq
|
|
|
|
chmod u+x jq
|
|
|
|
|
|
|
|
# Create manifest file
|
|
|
|
(
|
|
|
|
for i in segment_*; do
|
2018-10-19 18:51:17 -04:00
|
|
|
./jq -n --arg path "{{.SegmentPath}}/$i" \
|
2018-10-18 03:39:41 -04:00
|
|
|
--arg etag $(md5sum $i | cut -f1 -d' ') \
|
|
|
|
--arg size_bytes $(stat --printf "%s" $i) \
|
|
|
|
'{path: $path, etag: $etag, size_bytes: $size_bytes}'
|
|
|
|
done
|
|
|
|
) | ./jq -s . > manifest.json
|
|
|
|
|
2018-10-18 01:21:22 -04:00
|
|
|
# Authenticate
|
2018-10-18 00:23:22 -04:00
|
|
|
curl -D auth-headers -s -X GET \
|
|
|
|
-H "X-Storage-User: Storage-{{.AccountID}}:{{.Username}}" \
|
|
|
|
-H "X-Storage-Pass: {{.Password}}" \
|
|
|
|
https://{{.AccountID}}.storage.oraclecloud.com/auth/v1.0
|
2018-10-17 23:16:23 -04:00
|
|
|
|
|
|
|
export AUTH_TOKEN=$(awk 'BEGIN {FS=": "; RS="\r\n"}/^X-Auth-Token/{print $2}' auth-headers)
|
|
|
|
export STORAGE_URL=$(awk 'BEGIN {FS=": "; RS="\r\n"}/^X-Storage-Url/{print $2}' auth-headers)
|
|
|
|
|
2018-10-18 17:50:12 -04:00
|
|
|
# Create segment directory
|
2018-10-19 18:51:17 -04:00
|
|
|
curl -v -X PUT -H "X-Auth-Token: $AUTH_TOKEN" ${STORAGE_URL}/{{.SegmentPath}}
|
2018-10-17 23:16:23 -04:00
|
|
|
|
2018-10-18 01:21:22 -04:00
|
|
|
# Upload segments
|
|
|
|
for i in segment_*; do
|
2018-10-17 23:16:23 -04:00
|
|
|
curl -v -X PUT -T $i \
|
|
|
|
-H "X-Auth-Token: $AUTH_TOKEN" \
|
2018-10-19 18:51:17 -04:00
|
|
|
${STORAGE_URL}/{{.SegmentPath}}/$i;
|
2018-10-17 23:16:23 -04:00
|
|
|
done
|
|
|
|
|
2018-10-18 01:21:22 -04:00
|
|
|
# Create machine image from manifest
|
2018-10-18 00:23:22 -04:00
|
|
|
curl -v -X PUT \
|
|
|
|
-H "X-Auth-Token: $AUTH_TOKEN" \
|
2018-10-19 18:51:17 -04:00
|
|
|
"${STORAGE_URL}/compute_images/{{.ImageFile}}?multipart-manifest=put" \
|
2018-10-18 00:23:22 -04:00
|
|
|
-T ./manifest.json
|
2018-10-18 00:51:54 -04:00
|
|
|
|
2018-10-18 01:21:22 -04:00
|
|
|
# Get uploaded image description
|
|
|
|
curl -I -X HEAD \
|
|
|
|
-H "X-Auth-Token: $AUTH_TOKEN" \
|
2018-10-19 18:51:17 -04:00
|
|
|
"${STORAGE_URL}/compute_images/{{.ImageFile}}"
|
2018-10-18 00:51:54 -04:00
|
|
|
`
|
2018-09-12 19:16:08 -04:00
|
|
|
}
|
|
|
|
/*
|
|
|
|
errs = packer.MultiErrorAppend(errs,
|
|
|
|
fmt.Errorf("Persistent storage volumes are only supported on unix, and must use the ssh communicator."))
|
|
|
|
*/
|
|
|
|
return
|
|
|
|
}
|