# Parametrized pipeline from SCM

**URL:** <https://community.jenkins.io/t/parametrized-pipeline-from-scm/8002>\
**Category:** Ask a question\
**Created:** [June 14, 2023, 8:49am UTC](https://community.jenkins.io/t/parametrized-pipeline-from-scm/8002 "2023-06-14T08:49:58Z")\
**Posts on this page:** 6\
**Page:** 1

<div class="post-metadata">

**Author:** ![i8z](https://avatars.discourse-cdn.com/v4/letter/i/bbce88/32.png) [@i8z](https://community.jenkins.io/u/i8z)\
**Post date:** [June 14, 2023, 8:49am UTC](https://community.jenkins.io/t/parametrized-pipeline-from-scm/8002/1 "2023-06-14T08:49:58Z")

</div>

Hi everyone,

I have parametrized pipeline from SCM, something like this:

```auto
parameters {
    string(name: 'VAR1', description: 'some description', trim: true)
    string(name: 'VAR2', description: 'some description', trim: true)
    string(name: 'VAR3', description: 'some description', trim: true)
<... more parameters...>
}

```

I don’t have default values in this Jenkinsfile, since code is in git, therefore I don’t want to keep any sensitive data there.

My idea is to populate parameters fields from Jenkinsfile on 1st build, and enter respective values in UI, so that user can change it from time to time when needed.

But generally, I would like to keep those saved parameters in UI unchanged during each build.

So far, the only solution was to populate parameters fields in UI manually, and save values there (basically by removing parameters code block from Jenkinsfile).  
Because if I populate parameters from Jenkinsfile, all values from UI will disappear during next build.  
I’ve even tried to comment whole parameters code block after saving parameters in UI, but after next build all is gone (parameters and values).

Is there any workaround for my idea? I wouldn’t like to generate all parameters for each project/environment manually in UI. But if that’s the only way, I’ll survive 🙂

Thank you

---

<div class="post-metadata">

**Author:** ![poddingue](https://dub1.discourse-cdn.com/flex013/user_avatar/community.jenkins.io/poddingue/32/985_2.png) [@poddingue](https://community.jenkins.io/u/poddingue)\
**Post date:** [June 15, 2023, 6:50am UTC](https://community.jenkins.io/t/parametrized-pipeline-from-scm/8002/2 "2023-06-15T06:50:46Z")

</div>

Hello @i8z and welcome to this community 👋

I don’t see any elegant way to do what you need to.  
There’s maybe a plugin for that, but I don’t know any. 🤷

---

<div class="post-metadata">

**Author:** ![VladyslavKovalov](https://dub1.discourse-cdn.com/flex013/user_avatar/community.jenkins.io/vladyslavkovalov/32/4473_2.png) [@VladyslavKovalov](https://community.jenkins.io/u/VladyslavKovalov)\
**Post date:** [June 15, 2023, 8:26am UTC](https://community.jenkins.io/t/parametrized-pipeline-from-scm/8002/3 "2023-06-15T08:26:25Z")

</div>

Hi, @i8z !  
You should select one place to handle job parameters: Jenkinsfile or UI.  
You parameters disappear on next build because when you click Build button and build starts, it obtains Jenkinsfile from SCM, where different parameters are defined. So parameters that you’ve defined in UI has been overriden. Please note, that if you have properties block in your Jenkinsfile, that is already enough to override parameters, because parameters block is nested to properties. In this case you will receive empty parameters list.

---

<div class="post-metadata">

**Author:** ![i8z](https://avatars.discourse-cdn.com/v4/letter/i/bbce88/32.png) [@i8z](https://community.jenkins.io/u/i8z)\
**Post date:** [June 15, 2023, 9:56am UTC](https://community.jenkins.io/t/parametrized-pipeline-from-scm/8002/4 "2023-06-15T09:56:33Z")

</div>

Hi,  
Seems like I found some partial solution for this situation on Stack Overflow:

> <https://stackoverflow.com/questions/57745451/how-can-i-override-a-jenkinsfiles-default-parameters>

So this:

```auto
string(name: 'parameterName', defaultValue: params.parameterName ?:'your default value')

```

will preserve my parameters in UI from being overwritten by default value from Jenkinsfile/SCM

And that would be exactly what I wanted, but seems like this doesn’t work with passwords as mentioned in one of the comments.

@VladyslavKovalov I’ve tried already to nest my parameters under properties. Something like this:

```auto
properties([ 
  parameters([
    string(name: 'VAR1', description: 'some description', trim: true),
    string(name: 'VAR2', description: 'some description', trim: true),
    string(name: 'VAR3', description: 'some description', trim: true),
<... more parameters...>,
    ]) 
])

```

… but this fails with:  
`The ‘properties’ section has been renamed as of version 0.8. Use ‘options’ instead`

I even tried to rename properties =\> options, but I still end up with bunch of errors.

That’s why I gave up on `properties`.

I need those parameters in Jenkinsfile just to populate parameters fields in UI after first build, and then change them accordingly, because there are lot of properties there, and each project/environment has a different values there.

---

<div class="post-metadata">

**Author:** ![VladyslavKovalov](https://dub1.discourse-cdn.com/flex013/user_avatar/community.jenkins.io/vladyslavkovalov/32/4473_2.png) [@VladyslavKovalov](https://community.jenkins.io/u/VladyslavKovalov)\
**Post date:** [June 15, 2023, 12:27pm UTC](https://community.jenkins.io/t/parametrized-pipeline-from-scm/8002/5 "2023-06-15T12:27:35Z")

</div>

> [@i8z](#):
>
> The ‘properties’ section has been renamed as of version 0.8. Use ‘options’ instead

Really strange behavior. May be you are using declarative pipeline syntax instead of scripted pipeline. We are using Jenkins 2.387.3 LTS and `properties` notation works as expected. Here is the fragment of our Jenkinsfile:

```auto
properties([
    parameters([
        [$class: 'CascadeChoiceParameter',
            choiceType: 'PT_SINGLE_SELECT',
            name: 'ARTIFACT_PROJECT_NAME',
            description: "Project for copy image from",
            filterable: true,
            filterLength: 1,
            randomName: 'choice-parameter-9587366504630684',
            script: [
                $class: 'GroovyScript',
                fallbackScript: [script: 'return ["Failed to load projects"]'],
                script: [script: '''
def instances = []
for (instance in jenkins.model.Jenkins.instance.getAllItems()) {
    if (instance.getDescription() && instance.getDescription().contains("DeviceTesting")) {
        instances.add(instance.displayName)
    }
}
return instances
                '''
                ]
            ]
        ],
        [$class: 'CascadeChoiceParameter',
            choiceType: 'PT_CHECKBOX',
            description: 'Show all builds regardless its state',
            filterLength: 1,
            filterable: false,
            name: 'SHOW_FAILED_BUILDS',
            randomName: 'choice-parameter-5331064039195643',
            referencedParameters: '',
            script: [
                $class: 'GroovyScript',
                fallbackScript: [classpath: [], oldScript: '', sandbox: false, script: ''],
                script: [script: '''
return ['Show all builds']
                '''
                ]
            ]
        ],
        [$class: 'CascadeChoiceParameter',
            choiceType: 'PT_SINGLE_SELECT',
            name: 'ARTIFACT_BUILD_NUMBER',
            description: "Build number for copy image from",
            referencedParameters: 'ARTIFACT_PROJECT_NAME,SHOW_FAILED_BUILDS',
            filterable: true,
            filterLength: 1,
            randomName: 'choice-parameter-9513006304630684',
            script: [
                $class: 'GroovyScript',
                fallbackScript: [script: 'return ["Failed to load build numbers from PROJECT_NAME"]'],
                script: [script: '''
for (instance in jenkins.model.Jenkins.instance.getAllItems()) {
    if (instance.displayName == ARTIFACT_PROJECT_NAME) {
        def builds = []
        for (def build in instance.builds) {
            if (SHOW_FAILED_BUILDS == 'Show all builds') {
                builds.add(build.number)
            } else if (build.getResult().toString().equals("SUCCESS")) {
                builds.add(build.number)
            }
        }
        return builds
    }
}
                '''
                ]
            ]
        ]
    ])
])

```

Try to use pipeline snippet generator to generate parameters notation correctly. Pipeline snippet generator can be found by the following url pattern:  
[https://jenkins-url/job/pipeline\_job\_name/pipeline-syntax/](https://jenkins-url/job/pipeline_job_name/pipeline-syntax/)  
Here is how to do that:

 ![1](https://europe1.discourse-cdn.com/flex013/uploads/jenkins/original/2X/7/751fd362279575024f9221f11b1e2ad7bae8c2cd.png)  
 ![2](https://europe1.discourse-cdn.com/flex013/uploads/jenkins/original/2X/d/d214421d2f99b03ae07502c7d078f70b34dda37c.png)  
 ![3](https://europe1.discourse-cdn.com/flex013/uploads/jenkins/original/2X/7/77e434e8d5e913bb307ec48c9c89fa2f9099fb4b.png)

---

<div class="post-metadata">

**Author:** ![i8z](https://avatars.discourse-cdn.com/v4/letter/i/bbce88/32.png) [@i8z](https://community.jenkins.io/u/i8z)\
**Post date:** [June 16, 2023, 7:41am UTC](https://community.jenkins.io/t/parametrized-pipeline-from-scm/8002/6 "2023-06-16T07:41:10Z")

</div>

> May be you are using declarative pipeline syntax instead of scripted pipeline.

Ah, that explains why it didn’t work. My pipeline has been written using declarative syntax, so it’s no wonder why parameters cannot be nested within options, especially inside `([...])`. I didn’t realize until now that this syntax cannot be used in declarative pipeline.  
@VladyslavKovalov thanks for brief explanation.

Running Jenkins version on this project is the latest one, 2.401.1

So basically it turns out that whole code needs to be refactored to the scripted one because of that minor detail with passwords, which sound like a really huge amount of work at this moment. Not sure if it’s worth it.

So far, code:  
`string(name: 'VAR1', defaultValue: params.VAR1 ?:'default value')`  
does exactly what I wanted to do: _if there’s existing value already, don’t touch it. Othervise, provide default value._

Except the password parameter, ofc which I cannot figure out how to deal with it.  
If I try something like this:  
`password(name: 'PW1', defaultValue: params.PW1 ?:'dummypassword')`  
It basically erase existing password value on first build if it finds it there. If I try a second build (when password is already erased during previous build), then it provides default value. And over and over…

Workaround for that could be to convert password to string, but then it would be visible to anyone who runs the pipeline, which is bad idea.  
I’m sure that there must be a workaround for this issue.
