I want to create a config map that uses a JSON object for it's value
The JSON object looks something like this, (variable name = manifestJSON)
{
"appRepoVersionsMap": {
"repoA": "1.0.0.131",
"repoB": "1.0.0.7393"
},
"deployerVersion": "49",
"openshiftConfigCommitId": "o76to87y"
}
Then I want to create a configmap that takes this JSON object and adds it as a value of the configmap.
The command I am trying to make it work is
def osCmd = "create configmap manifest-config" +
" --from-literal=manifest.os_config_branch=${envVars.OS_CONFIG_BRANCH}" +
" --from-literal=manifest.os_server=${envVars.OPENSHIFT_SERVER_URL}"
" --from-literal=manifest.os_manifest=${manifestJSON}"
os.call(osCmd)
OpenShift client gives the following error:
10:23:37 error: cannot add key manifest.os_manifest, another key by that name already exists: map[manifest.os_config_branch:deployment-orchestrator manifest.os_server:<snipped>, manifest.os_manifest:appRepoVersionsMap:repoA:1.0.0.131 ].
So either groovy or OpenShift sees the JSON object within the JSON object and can't handle it.
I am trying to avoid using --from-file because I will have to write to disk and then run the command and I am afraid this will cause issues in a Jenkins environment with multiple deploys to multiple projects taking place.
The solution ended up being rather simple and I was overthinking the character escapes while trying various solutions.
In order to use a JSON as value when creating a configmap (or a secret) is to add '' around the JSON object itself
def osCmd = "create configmap manifest-config" +
" --from-literal=manifest.os_config_branch=${envVars.OS_CONFIG_BRANCH}" +
" --from-literal=manifest.os_server=${envVars.OPENSHIFT_SERVER_URL}"
" --from-literal=manifest.os_manifest='${manifestJSON}'" // <----- single quotes
os.call(osCmd)
That allowed the configmap creation and I confirmed from the OpenShift side that the configmap is present with the manifest values I was expecting.
Related
I would like to retrieve the public IP address associated with a given network interface. I need to do something like
client = NetworkManagementClient(...)
interface = client.network_interfaces.get('rg', 'nic-name')
ip_config_id = interface[0].public_ip_address.id
ip_config = some_magic(ip_config_id) # What goes here?
return ip_config.ip_address
This question suggests that in order to implement the some_magic routine, I should parse the ID (by splitting on slashes) and call client.public_ip_addresses.get(). This question indicates that I can call resource_client.resources.get_by_uid, but that doesn't return a PublicIPAddress object (I know I can call as_dict on it and get the data that way).
Is there a way to get an object of the appropriate type (in this case PublicIPAddress) from an object's ID in Azure (without manually parsing the ID)?
Update:
Due to this issue: public_ip_address method within NetworkManagementClient will not return values, we cannot fetch the ip address from PublicIPAddress.
So currently, you can use any other workaround, For example:
myip = client.public_ip_addresses.get(" resource_group_name","public_ip_address_name")
print(myip.ip_address)
You can change this line of code ip_config_id = interface[0].public_ip_address.id to something like my_public_ip_address = interface.ip_configurations[0].public_ip_address, then the return type is PublicIPAddress.
For example:
I am trying to pass multiple values to pricipals's identifiers in the data resource "aws_iam_policy_document". getting the following error
Inappropriate value for attribute "identifiers": element 0: string required.
s3_values variable is defined type = any and set the values as
....
s3_values:
bucket: bucketname1
s3_arns:
- arn:aws:iam::1234567890:root
- arn:aws:iam::2345678901:role/s3-read-role
data "aws_iam_policy_document" "s3_policy" {
count = length(var.s3_arns)
statement {
sid = "1"
effect = "Allow"
principals {
type = "AWS"
identifiers = ["${var.s3_values[count.index]["s3_arns"]}"]
}
actions = ["s3:PutObject"]
resources = ["arn:aws:s3:::${var.s3_values[count.index]["bucket"]}/*"]
}
}
I get the following error
Inappropriate value for attribute "identifiers": element 0: string required.
its working , when only one value is passed , but not working when we pass multiple values to the variable s3_arns.
It looks like you're trying to create multiple policy documents for a single S3 bucket. Rather than using count to create many documents, it would be best if you created a single policy document that gives access to each ARN you pass.
Currently it works for one ARN because the identifiers field gets passed a single string and creates a list with one string element. When you pass a list of ARNs, the identifiers field is instead creating a list with a list element that contains the ARN strings.
I would fix this by making the s3_arns field always be a list of strings, and removing the count field on the data resource. Once you do that you can change the line identifiers to be identifiers = var.s3_values.s3_arns and the resources line to be resources = ["arn:aws:s3:::${var.s3_values.bucket}/*"]
I'm using MPXJ to read projects from both Primavera and MSP and would like to read the user field definition information e.g. the field label / description, any ideas how this can be achieved ?
The detail you are looking for can be found by calling the getCustomFields method of a ProjectFile instance. You can either iterate through the contents of the container this method returns to see the configuration for all fields:
for (CustomField field : projectFile.getCustomFields())
{
System.out.println("Field: " + field.getFieldType() +
" Alias: " + field.getAlias());
}
or you can call getCustomField and pass a FieldType instance to look for the configuration of a specific field, for example:
projectFile.getCustomFields().getCustomField(TaskField.TEXT1)
I need to be able to get some slave information to be used in one of my jobs.
I have a Groovy system script to access the slave information
for (aSlave in hudson.model.Hudson.instance.slaves) {
println('====================');
println('Name: ' + aSlave.name);
println('getLabelString: ' + aSlave.getLabelString());
... In here I can dig out the information that I need
}
Is there a way how I can get the information back to use in a Post Build Job?
I need to add the output to a parameter or something that can be used by a Post Build Job?
If you are running windows I have got a solution for you: You can save your settings into environment varables, which are usable for the currently running job. They will no longer exist once the job is finished, but they are usable for post-build action. Here is an example:
//Creating String to make my example more clear
String myString = 'this is just a test!';
//Create an environment variable, so the Jenkins job can use the parameter
def pa = new ParametersAction([new StringParameterValue('PARAMETER_NAME', myString)]);
// Add variable to current jobs environment variables.
Thread.currentThread().executable.addAction(pa)
println 'Script finished! \n';
After the script ran you can use %PARAMETER_NAME% (if post-build-actions etc.) to gain access to its content.
Additional Hint: To see all available environment variables you can use the build step "execute windows batch command" and click on "See the list of available environment variables" on the buttom (the variables you create while executing scripts are excluded). But you can use these variables within your groovy script using e.g.:
String jenkinsHome = System.getenv('JENKINS_HOME');
I used The EnjEnv plugin and it has a 'Evaludated Groovy Script' section that basically you can do anything... but it should return a property map that will be used as Environment variables. I don't know how to return a value from a Groovy script so this worked kewl for me as I can reference property (or Environment variables) from almost anyware
import hudson.model.*
String labelIWantServersOf = TheLabelUsedOnTheElasticAxisPlugin; // This is the label assosiated with nodes for which i want the server names of
String serverList = '';
for (aSlave in hudson.model.Hudson.instance.slaves) {
out.println('Evaluating Server(' + aSlave.name + ') with label = ' + aSlave.getLabelString());
if (aSlave.getLabelString().indexOf(labelIWantServersOf ) > -1) {
serverList += aSlave.name + ' ';
out.println('Valid server found: ' + aSlave.name);
}
}
out.println('Final server list where SOAP projects will run on = ' + serverList + ' which will be used in the environment envInject map');
Map<String, String> myMap = new HashMap<>(2);
myMap.put("serverNamesToExecuteSoapProjectOn", serverList );
return myMap;
And then I write the environment variable serverNamesToExecuteSoapProjectOn to a property file using a windows batch script and pass the property file to the next build as a parameterized build
My requirement is to do some repetitive file configuration stuff using a loop, Something like following,
$no_of_managers = 2
$array = ['One','two','Three']
define loop() {
notice("Configuring The Manager Nodes!!")
if ($name == $no_of_managers+1) {
notice("Loop Iteration Finished!!!")
}
else
{
notice("Iteration Number : $name \n")
# Doing All Stuff Here
resource {$array:}
$next = $name + 1
loop { $next: }
}
}
loop { "1":}
define resource () {
# Doing my other Stuff
notice ("The Parsed value Name : ${name}\n")
}
Now when The second iteration is running the following error occurs,
Error: Duplicate declaration: Resource[One] is already declared in file
How can I overcome this, What I'm doing is a cluster setup. Is there a workaround to do this, I'm a newbie for puppet so Your kind guidance highly appreciated.
The Use Case :
I'm trying to setup a cluster which have multiple Manager/Worker nodes, So using this script the user has the privilege to select how many manager nodes he needs. So the first loop is for that to copy necessary files and create required number of nodes.
The second loop is there to push all .erb templates. Because each Node has slightly different configs the .erb files have there own logic inside them.
So after each Iteration I want to push the .erb templates to the respective node.
In Puppet 3.x, you cannot build a loop in the fashion you are trying.
resource { $array: }
is a loop over the contents of $array if you will.
It is not really clear what you are trying to solve. If you can make your question a bit more concrete, we may be able to suggest an actual implementation.
Update
If you really want to go down this road, you need to generate unique names for your derived resources.
$local_names = regsubst($array, '$', "-$name")
resource { $local_names: }
In your defined type, you will have to retrieve the original meaning by removing the suffix.
define resource() {
$orig_name = regsubst($name, '-[0-9]+$', '')
# use $orig_name where you used $name before
}
Note that even exported resources must have unique names. So the transformation may have to happen on in the manifest of the receiving node.