-
Notifications
You must be signed in to change notification settings - Fork 45
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Integrate new probe interface into GCP framework (#259)
* add gcp_curl_probe * change startup-script to split printing and curl service to print userdata begin runs multiple times despite succeeding. service to run curl fails. printing end token requires curl to succeed so it does not start running. crash recovery kernel arming runs everytime vm is created. * added shell script to run curl and access config shell script prints starting and ending token and runs curl. shell script checks if command was successful. also added external IP so curl has an output * add systemd instance termination after set delay used a systemd script and shell script that gets GCP NAME and ZONE so the instance self deletes. this ensures that if something happens to the client, the resource is not left on customer accounts. * silence kernel completely and fetch egress URLs Egress URLs are fetched from GitHub as done in the AWS verifier * remove target after multi-user target after multi-user unneeded because other outputs are completely silenced and wont interfere with probe output * ignore curl error codes that are network errors systemd service that runs curl should only fail if bash script returns an error code, this happens if curl error code is 1-4, 27, 41-43, 45 which means curl failed, not a network failure * update startup-script and gcp probe comments * combine GCP curl probe into AWS curl probe added userDataTemplate to the probe interface so getExpandedUserData can take in different templates for GCP and AWS * Update pkg/probes/legacy/legacy.go Co-authored-by: Alex Vulaj <ajvulaj@gmail.com> * Update pkg/verifier/aws/entry_point.go Co-authored-by: Alex Vulaj <ajvulaj@gmail.com> * clean code * change startup-script to use all userDataVariables made minor changes to curl probe to make more readible and added functionality to startup-script to add cacerts and export proxy environment variables if specified * revert probe interface and pass platform as map a workaround of not changing the probe interface and using a different template for GetExpandedUserData is to pass a userDataVariable through the probe interface. In the GetExpandedUserData, based off if a GCP platform exists, the function chooses userdata-template or startup-script. also changed gcp verifier to use GetMachineImageID which sets default machine image. * remove unused testing function * remove unused packages and add comment * use CPUArchitecture.DefaultInstanceType function * add error * Update comment for userDataVariable Co-authored-by: Anthony Byrne <abyrne@redhat.com> * Change time unit to seconds Co-authored-by: Anthony Byrne <abyrne@redhat.com> * import time * change get_tokens function to camel case --------- Co-authored-by: Alex Vulaj <ajvulaj@gmail.com> Co-authored-by: Anthony Byrne <abyrne@redhat.com>
- Loading branch information
1 parent
90e5f19
commit e338e54
Showing
7 changed files
with
286 additions
and
33 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,83 @@ | ||
#!/bin/sh | ||
# GCP compute engine copies startup script to VM and runs script as root when the VM boots | ||
|
||
# get name and zone needed for instance deletion from compute metadata server | ||
cat <<EOF > /usr/bin/terminate.sh | ||
#! /bin/sh | ||
if gcloud --quiet compute instances delete $(curl -X GET http://metadata.google.internal/computeMetadata/v1/instance/name -H 'Metadata-Flavor: Google') --zone=$(curl -X GET http://metadata.google.internal/computeMetadata/v1/instance/zone -H 'Metadata-Flavor: Google'); then : ; else | ||
exit 255 | ||
fi | ||
EOF | ||
|
||
# print curl output and tokens to serial output for client | ||
cat <<'EOF' > /usr/bin/curl.sh | ||
#! /bin/sh | ||
array=(1 2 3 4 27 41 42 43 45) | ||
if echo ${USERDATA_BEGIN} > /dev/ttyS0 ; then : ; else | ||
exit 255 | ||
fi | ||
curl --retry 3 --retry-connrefused -t B -Z -s -I -m ${TIMEOUT} -w "%{stderr}${LINE_PREFIX}%{json}\n" ${CURLOPT} ${URLS} --proto =http,https,telnet ${TLSDISABLED_URLS_RENDERED} 2>/dev/ttyS0 | ||
ret=$? | ||
value="\<${ret}\>" | ||
if [[ " ${array[@]} " =~ $value ]]; then | ||
exit 255 | ||
fi | ||
if echo ${USERDATA_END} > /dev/ttyS0 ; then : ; else | ||
exit 255 | ||
fi | ||
EOF | ||
|
||
# create systemd units for silencing serial console, running curl and deleting instance | ||
cat <<EOF > /etc/systemd/system/silence.service | ||
[Unit] | ||
Description=Serial Console Silencing Service | ||
[Service] | ||
Type=oneshot | ||
ExecStart=systemctl mask --now serial-getty@ttyS0.service | ||
ExecStart=systemctl disable --now syslog.socket rsyslog.service | ||
ExecStart=sysctl -w kernel.printk="0 4 0 7" | ||
ExecStart=kill -SIGRTMIN+21 1 | ||
Restart=on-failure | ||
[Install] | ||
WantedBy=multi-user.target | ||
EOF | ||
cat <<EOF > /etc/systemd/system/curl.service | ||
[Unit] | ||
Description=Curl Output Service | ||
[Service] | ||
Type=oneshot | ||
ExecStart=/usr/bin/curl.sh | ||
Restart=on-failure | ||
RemainAfterExit=true | ||
[Install] | ||
WantedBy=multi-user.target | ||
EOF | ||
cat <<EOF > /etc/systemd/system/terminate.service | ||
[Unit] | ||
Description=Compute Instance Deletion Service | ||
[Service] | ||
Type=oneshot | ||
ExecStart=/usr/bin/terminate.sh | ||
Restart=on-failure | ||
EOF | ||
cat <<EOF > /etc/systemd/system/terminate.timer | ||
[Unit] | ||
Description=Instance Deletion Timer | ||
[Timer] | ||
OnBootSec=${DELAY}min | ||
Unit=terminate.service | ||
[Install] | ||
WantedBy=multi-user.target | ||
EOF | ||
|
||
# if cacert is provided, curl probe adds CURLOPT to use the provided cacert | ||
echo "${CACERT}" | base64 > /proxy.pem | ||
chmod 0755 /proxy.pem | ||
|
||
# set proxy environment variables, make script executable and start systemd services | ||
export http_proxy=${HTTP_PROXY} https_proxy=${HTTPS_PROXY} | ||
chmod 777 /usr/bin/curl.sh /usr/bin/terminate.sh | ||
systemctl daemon-reload | ||
systemctl start silence | ||
systemctl start curl | ||
systemctl start terminate.timer |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,44 @@ | ||
package gcpverifier | ||
|
||
import ( | ||
"fmt" | ||
"strings" | ||
|
||
"github.com/openshift/osd-network-verifier/pkg/helpers" | ||
"github.com/openshift/osd-network-verifier/pkg/probes" | ||
) | ||
|
||
// function that tests probe order logic that is part of findUnreachableEndpoints in gcp_verifier.go | ||
// get_tokens checks for the presence of startingToken and endingToken in the consoleOutput | ||
// probe outsput should be between startingToken and endingToken | ||
func getTokens(consoleOutput string, probe probes.Probe) bool { | ||
// Check for startingToken and endingToken | ||
startingTokenSeen := strings.Contains(consoleOutput, probe.GetStartingToken()) | ||
endingTokenSeen := strings.Contains(consoleOutput, probe.GetEndingToken()) | ||
if !startingTokenSeen { | ||
if endingTokenSeen { | ||
fmt.Printf("raw console logs:\n---\n%s\n---", consoleOutput) | ||
fmt.Printf("probe output corrupted: endingToken encountered before startingToken") | ||
return false | ||
} | ||
fmt.Printf("consoleOutput contains data, but probe has not yet printed startingToken, continuing to wait...") | ||
return false | ||
} | ||
if !endingTokenSeen { | ||
fmt.Printf("consoleOutput contains data, but probe has not yet printed endingToken, continuing to wait...") | ||
return false | ||
} | ||
// If we make it this far, we know that both startingTokenSeen and endingTokenSeen are true | ||
|
||
// Separate the probe's output from the rest of the console output (using startingToken and endingToken) | ||
rawProbeOutput := strings.TrimSpace(helpers.CutBetween(consoleOutput, probe.GetStartingToken(), probe.GetEndingToken())) | ||
if len(rawProbeOutput) < 1 { | ||
fmt.Printf("raw console logs:\n---\n%s\n---", consoleOutput) | ||
fmt.Printf("probe output corrupted: no data between startingToken and endingToken") | ||
return false | ||
} | ||
// Send probe's output off to the Probe interface for parsing | ||
fmt.Printf("probe output:\n---\n%s\n---", rawProbeOutput) | ||
|
||
return true | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,60 @@ | ||
package gcpverifier | ||
|
||
import ( | ||
"testing" | ||
|
||
"github.com/openshift/osd-network-verifier/pkg/probes" | ||
"github.com/openshift/osd-network-verifier/pkg/probes/curl" | ||
) | ||
|
||
func TestGetTokens(t *testing.T) { | ||
type args struct { | ||
consoleOutput string | ||
probe probes.Probe | ||
} | ||
tests := []struct { | ||
name string | ||
args args | ||
want bool | ||
}{ | ||
{ | ||
name: "tokens in order", | ||
args: args{ | ||
consoleOutput: "otherinfoNV_CURLJSON_BEGIN\nhello world\nNV_CURLJSON_END\njj", | ||
probe: curl.Probe{}, | ||
}, | ||
want: true, | ||
}, | ||
{ | ||
name: "only start token", | ||
args: args{ | ||
consoleOutput: "NV_CURLJSON_BEGIN\nhello world\n", | ||
probe: curl.Probe{}, | ||
}, | ||
want: false, | ||
}, | ||
{ | ||
name: "only end token", | ||
args: args{ | ||
consoleOutput: "hello world\nNV_CURLJSON_END\njj", | ||
probe: curl.Probe{}, | ||
}, | ||
want: false, | ||
}, | ||
{ | ||
name: "token order reversed", | ||
args: args{ | ||
consoleOutput: "fjsdklNV_CURLJSON_END\nhello world\nNV_CURLJSON_BEGIN\njj", | ||
probe: curl.Probe{}, | ||
}, | ||
want: false, | ||
}, | ||
} | ||
for _, tt := range tests { | ||
t.Run(tt.name, func(t *testing.T) { | ||
if got := getTokens(tt.args.consoleOutput, tt.args.probe); got != tt.want { | ||
t.Errorf("get_tokens() = %v, want %v", got, tt.want) | ||
} | ||
}) | ||
} | ||
} |