Full Code of jenkinsci/jira-plugin for AI

master 61f365c12335 cached
300 files
775.0 KB
183.7k tokens
1297 symbols
1 requests
Download .txt
Showing preview only (870K chars total). Download the full file or copy to clipboard to get everything.
Repository: jenkinsci/jira-plugin
Branch: master
Commit: 61f365c12335
Files: 300
Total size: 775.0 KB

Directory structure:
gitextract_wo4b4tn0/

├── .git-blame-ignore-revs
├── .github/
│   ├── CODEOWNERS
│   ├── FUNDING.yml
│   ├── ISSUE_TEMPLATE/
│   │   ├── 1-report-bug.yml
│   │   ├── 2-feature-request.yml
│   │   ├── 3-documentation.yml
│   │   └── config.yml
│   ├── pull_request_template.md
│   ├── release-drafter.yml
│   ├── renovate.json
│   └── workflows/
│       ├── crowdin.yml
│       ├── jenkins-security-scan.yml
│       ├── release-drafter.yml
│       └── sonarcloud.yml
├── .gitignore
├── .mvn/
│   ├── extensions.xml
│   └── maven.config
├── .pre-commit-config.yaml
├── CONTRIBUTING.md
├── Jenkinsfile
├── LICENSE.md
├── README.md
├── crowdin.yml
├── docker-compose.yml
├── docs/
│   ├── .nojekyll
│   ├── README.md
│   ├── _sidebar.md
│   ├── changelog.md
│   ├── features.md
│   ├── index.html
│   ├── system-properties.md
│   ├── troubleshooting.md
│   └── usage-examples.md
├── pom.xml
└── src/
    ├── main/
    │   ├── java/
    │   │   ├── com/
    │   │   │   └── atlassian/
    │   │   │       └── httpclient/
    │   │   │           ├── apache/
    │   │   │           │   └── httpcomponents/
    │   │   │           │       ├── ApacheAsyncHttpClient.java
    │   │   │           │       ├── CommonBuilder.java
    │   │   │           │       ├── CompletableFuturePromiseHttpPromiseAsyncClient.java
    │   │   │           │       ├── DefaultHttpClientFactory.java
    │   │   │           │       ├── DefaultMessage.java
    │   │   │           │       ├── DefaultRequest.java
    │   │   │           │       ├── DefaultResponse.java
    │   │   │           │       ├── EntityByteArrayInputStream.java
    │   │   │           │       ├── Headers.java
    │   │   │           │       ├── MavenUtils.java
    │   │   │           │       ├── PromiseHttpAsyncClient.java
    │   │   │           │       ├── RedirectStrategy.java
    │   │   │           │       └── RequestEntityEffect.java
    │   │   │           └── base/
    │   │   │               └── event/
    │   │   │                   ├── AbstractHttpRequestEvent.java
    │   │   │                   ├── HttpRequestCompletedEvent.java
    │   │   │                   └── HttpRequestFailedEvent.java
    │   │   └── hudson/
    │   │       └── plugins/
    │   │           └── jira/
    │   │               ├── CredentialsHelper.java
    │   │               ├── EmptyFriendlyURLConverter.java
    │   │               ├── EnvironmentExpander.java
    │   │               ├── JiraBuildAction.java
    │   │               ├── JiraCarryOverAction.java
    │   │               ├── JiraChangeLogAnnotator.java
    │   │               ├── JiraCreateIssueNotifier.java
    │   │               ├── JiraCreateReleaseNotes.java
    │   │               ├── JiraEnvironmentContributingAction.java
    │   │               ├── JiraEnvironmentVariableBuilder.java
    │   │               ├── JiraFolderProperty.java
    │   │               ├── JiraGlobalConfiguration.java
    │   │               ├── JiraIssueMigrator.java
    │   │               ├── JiraIssueUpdateBuilder.java
    │   │               ├── JiraIssueUpdater.java
    │   │               ├── JiraJobAction.java
    │   │               ├── JiraMailAddressResolver.java
    │   │               ├── JiraProjectProperty.java
    │   │               ├── JiraReleaseVersionUpdater.java
    │   │               ├── JiraReleaseVersionUpdaterBuilder.java
    │   │               ├── JiraRestService.java
    │   │               ├── JiraSession.java
    │   │               ├── JiraSessionFactory.java
    │   │               ├── JiraSite.java
    │   │               ├── JiraVersionCreator.java
    │   │               ├── JiraVersionCreatorBuilder.java
    │   │               ├── RunScmChangeExtractor.java
    │   │               ├── Updater.java
    │   │               ├── VersionCreator.java
    │   │               ├── VersionReleaser.java
    │   │               ├── auth/
    │   │               │   └── BearerHttpAuthenticationHandler.java
    │   │               ├── extension/
    │   │               │   ├── ExtendedAsynchronousJiraRestClient.java
    │   │               │   ├── ExtendedAsynchronousMyPermissionsRestClient.java
    │   │               │   ├── ExtendedAsynchronousVersionRestClient.java
    │   │               │   ├── ExtendedJiraRestClient.java
    │   │               │   ├── ExtendedMyPermissionsRestClient.java
    │   │               │   ├── ExtendedVersion.java
    │   │               │   ├── ExtendedVersionInput.java
    │   │               │   ├── ExtendedVersionInputJsonGenerator.java
    │   │               │   ├── ExtendedVersionJsonParser.java
    │   │               │   └── ExtendedVersionRestClient.java
    │   │               ├── listissuesparameter/
    │   │               │   ├── JiraIssueParameterDefinition.java
    │   │               │   └── JiraIssueParameterValue.java
    │   │               ├── model/
    │   │               │   ├── JiraIssue.java
    │   │               │   ├── JiraIssueField.java
    │   │               │   └── JiraVersion.java
    │   │               ├── pipeline/
    │   │               │   ├── CommentStep.java
    │   │               │   ├── IssueFieldUpdateStep.java
    │   │               │   ├── IssueSelectorStep.java
    │   │               │   └── SearchIssuesStep.java
    │   │               ├── selector/
    │   │               │   ├── AbstractIssueSelector.java
    │   │               │   ├── DefaultIssueSelector.java
    │   │               │   ├── ExplicitIssueSelector.java
    │   │               │   ├── JqlIssueSelector.java
    │   │               │   └── perforce/
    │   │               │       ├── JobIssueSelector.java
    │   │               │       └── P4JobIssueSelector.java
    │   │               └── versionparameter/
    │   │                   ├── JiraVersionParameterDefinition.java
    │   │                   ├── JiraVersionParameterValue.java
    │   │                   └── VersionComparator.java
    │   ├── resources/
    │   │   ├── atlassian-httpclient-plugin-0.23.0.pom
    │   │   ├── hudson/
    │   │   │   └── plugins/
    │   │   │       └── jira/
    │   │   │           ├── JiraBuildAction/
    │   │   │           │   └── summary.jelly
    │   │   │           ├── JiraCreateIssueNotifier/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-actionIdOnSuccess.html
    │   │   │           │   ├── help-assignee.html
    │   │   │           │   ├── help-component.html
    │   │   │           │   ├── help-priorityId.html
    │   │   │           │   ├── help-projectKey.html
    │   │   │           │   ├── help-testDescription.html
    │   │   │           │   └── help-typeId.html
    │   │   │           ├── JiraCreateReleaseNotes/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-jiraEnvironmentVariable.html
    │   │   │           │   ├── help-jiraFilter.html
    │   │   │           │   ├── help-jiraProjectKey.html
    │   │   │           │   └── help-jiraRelease.html
    │   │   │           ├── JiraEnvironmentVariableBuilder/
    │   │   │           │   ├── config.jelly
    │   │   │           │   └── help.html
    │   │   │           ├── JiraFolderProperty/
    │   │   │           │   └── config.jelly
    │   │   │           ├── JiraGlobalConfiguration/
    │   │   │           │   └── config.jelly
    │   │   │           ├── JiraIssueMigrator/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-addRelease.html
    │   │   │           │   ├── help-jiraProjectKey.html
    │   │   │           │   ├── help-jiraQuery.html
    │   │   │           │   ├── help-jiraRelease.html
    │   │   │           │   └── help-jiraReplaceVersion.html
    │   │   │           ├── JiraIssueUpdateBuilder/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-comment.html
    │   │   │           │   ├── help-jqlSearch.html
    │   │   │           │   ├── help-workflowActionName.html
    │   │   │           │   └── help.html
    │   │   │           ├── JiraIssueUpdater/
    │   │   │           │   └── config.jelly
    │   │   │           ├── JiraProjectProperty/
    │   │   │           │   └── config.jelly
    │   │   │           ├── JiraReleaseVersionUpdater/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-jiraDescription.html
    │   │   │           │   ├── help-jiraProjectKey.html
    │   │   │           │   └── help-jiraRelease.html
    │   │   │           ├── JiraReleaseVersionUpdaterBuilder/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-jiraDescription.html
    │   │   │           │   ├── help-jiraProjectKey.html
    │   │   │           │   └── help-jiraRelease.html
    │   │   │           ├── JiraSite/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── config.properties
    │   │   │           │   ├── config_de.properties
    │   │   │           │   ├── config_fr.properties
    │   │   │           │   ├── config_it.properties
    │   │   │           │   ├── config_ja.properties
    │   │   │           │   ├── config_nl.properties
    │   │   │           │   ├── config_pl.properties
    │   │   │           │   ├── help-alternativeUrl.html
    │   │   │           │   ├── help-appendChangeTimestamp.html
    │   │   │           │   ├── help-credentialsId.html
    │   │   │           │   ├── help-credentialsId_de.html
    │   │   │           │   ├── help-credentialsId_fr.html
    │   │   │           │   ├── help-credentialsId_ja.html
    │   │   │           │   ├── help-dateTimePattern.html
    │   │   │           │   ├── help-disableChangelogAnnotations.html
    │   │   │           │   ├── help-groupVisibility.html
    │   │   │           │   ├── help-maxIssuesFromJqlSearch.html
    │   │   │           │   ├── help-readTimeout.html
    │   │   │           │   ├── help-recordScmChanges.html
    │   │   │           │   ├── help-recordScmChanges_fr.html
    │   │   │           │   ├── help-recordScmChanges_ja.html
    │   │   │           │   ├── help-roleVisibility.html
    │   │   │           │   ├── help-supportsWikiStyleComment.html
    │   │   │           │   ├── help-supportsWikiStyleComment_de.html
    │   │   │           │   ├── help-supportsWikiStyleComment_fr.html
    │   │   │           │   ├── help-supportsWikiStyleComment_ja.html
    │   │   │           │   ├── help-threadExecutorNumber.html
    │   │   │           │   ├── help-timeout.html
    │   │   │           │   ├── help-updateJiraIssueForAllStatus.html
    │   │   │           │   ├── help-url.html
    │   │   │           │   ├── help-url_de.html
    │   │   │           │   ├── help-url_fr.html
    │   │   │           │   ├── help-url_ja.html
    │   │   │           │   ├── help-useHTTPAuth.html
    │   │   │           │   ├── help-userPattern.html
    │   │   │           │   ├── help-userPattern_de.html
    │   │   │           │   ├── help-userPattern_fr.html
    │   │   │           │   └── help-userPattern_ja.html
    │   │   │           ├── JiraVersionCreator/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-failIfAlreadyExists.html
    │   │   │           │   ├── help-jiraProjectKey.html
    │   │   │           │   └── help-jiraVersion.html
    │   │   │           ├── JiraVersionCreatorBuilder/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-failIfAlreadyExists.html
    │   │   │           │   ├── help-jiraProjectKey.html
    │   │   │           │   └── help-jiraVersion.html
    │   │   │           ├── MavenJiraIssueUpdater/
    │   │   │           │   └── config.jelly
    │   │   │           ├── Messages.properties
    │   │   │           ├── Messages_de.properties
    │   │   │           ├── Messages_fr.properties
    │   │   │           ├── Messages_it.properties
    │   │   │           ├── Messages_ja.properties
    │   │   │           ├── Messages_pl.properties
    │   │   │           ├── listissuesparameter/
    │   │   │           │   ├── JiraIssueParameterDefinition/
    │   │   │           │   │   ├── config.jelly
    │   │   │           │   │   ├── help-altSummaryFields.html
    │   │   │           │   │   ├── help-jiraIssueFilter.html
    │   │   │           │   │   └── index.jelly
    │   │   │           │   └── JiraIssueParameterValue/
    │   │   │           │       └── value.jelly
    │   │   │           ├── pipeline/
    │   │   │           │   ├── CommentStep/
    │   │   │           │   │   └── config.jelly
    │   │   │           │   ├── IssueFieldUpdateStep/
    │   │   │           │   │   ├── config.jelly
    │   │   │           │   │   ├── help-fieldId.html
    │   │   │           │   │   └── help.html
    │   │   │           │   ├── IssueSelectorStep/
    │   │   │           │   │   └── config.jelly
    │   │   │           │   └── SearchIssuesStep/
    │   │   │           │       └── config.jelly
    │   │   │           ├── selector/
    │   │   │           │   ├── DefaultIssueSelector/
    │   │   │           │   │   └── config.jelly
    │   │   │           │   ├── ExplicitIssueSelector/
    │   │   │           │   │   └── config.jelly
    │   │   │           │   ├── JqlIssueSelector/
    │   │   │           │   │   └── config.jelly
    │   │   │           │   └── perforce/
    │   │   │           │       ├── P4JobIssueSelector/
    │   │   │           │       │   └── config.jelly
    │   │   │           │       └── PerforceJobIssueSelector/
    │   │   │           │           └── config.jelly
    │   │   │           └── versionparameter/
    │   │   │               ├── JiraVersionParameterDefinition/
    │   │   │               │   ├── config.jelly
    │   │   │               │   ├── help-jiraProjectKey.html
    │   │   │               │   ├── help-jiraReleasePattern.html
    │   │   │               │   ├── help-jiraShowReleased.html
    │   │   │               │   └── index.jelly
    │   │   │               └── JiraVersionParameterValue/
    │   │   │                   └── value.jelly
    │   │   └── index.jelly
    │   └── webapp/
    │       ├── help-jira-create-issue.html
    │       ├── help-release-migrate.html
    │       ├── help-release.html
    │       ├── help-version-create.html
    │       ├── help.html
    │       ├── help_de.html
    │       ├── help_fr.html
    │       └── help_ja.html
    ├── spotbugs/
    │   └── excludesFilter.xml
    └── test/
        ├── java/
        │   ├── JiraConfig.java
        │   ├── JiraTester.java
        │   ├── JiraTesterBearerAuth.java
        │   ├── com/
        │   │   └── atlassian/
        │   │       └── httpclient/
        │   │           └── apache/
        │   │               └── httpcomponents/
        │   │                   ├── ApacheAsyncHttpClientTest.java
        │   │                   └── CompletableFuturePromiseHttpPromiseAsyncClientTest.java
        │   └── hudson/
        │       └── plugins/
        │           └── jira/
        │               ├── BuildListenerResultMethodMock.java
        │               ├── ChangingWorkflowTest.java
        │               ├── CliParameterTest.java
        │               ├── ConfigAsCodeTest.java
        │               ├── CredentialsHelperTest.java
        │               ├── DescriptorImplTest.java
        │               ├── EmptyFriendlyURLConverterTest.java
        │               ├── EnvironmentExpanderTest.java
        │               ├── JiraBuildActionTest.java
        │               ├── JiraChangeLogAnnotatorTest.java
        │               ├── JiraCreateIssueNotifierTest.java
        │               ├── JiraCreateReleaseNotesTest.java
        │               ├── JiraEnvironmentContributingActionTest.java
        │               ├── JiraEnvironmentVariableBuilderTest.java
        │               ├── JiraFolderPropertyTest.java
        │               ├── JiraGlobalConfigurationSaveTest.java
        │               ├── JiraGlobalConfigurationTest.java
        │               ├── JiraIssueMigratorTest.java
        │               ├── JiraIssueParameterDefResultTest.java
        │               ├── JiraIssueUpdateBuilderTest.java
        │               ├── JiraIssueUpdaterTest.java
        │               ├── JiraJobActionTest.java
        │               ├── JiraProjectPropertyTest.java
        │               ├── JiraReleaseVersionUpdateBuilderTest.java
        │               ├── JiraRestServiceProxyTest.java
        │               ├── JiraRestServiceTest.java
        │               ├── JiraSessionTest.java
        │               ├── JiraSiteSecurity1029Test.java
        │               ├── JiraSiteTest.java
        │               ├── JiraVersionCreatorBuilderTest.java
        │               ├── MailResolverDisabledTest.java
        │               ├── MailResolverWithExtensionTest.java
        │               ├── MockAffectedFile.java
        │               ├── UnmaskMailTest.java
        │               ├── UpdaterTest.java
        │               ├── VersionCreatorTest.java
        │               ├── VersionReleaserTest.java
        │               ├── auth/
        │               │   ├── BearerHttpAuthenticationHandlerTest.java
        │               │   └── JiraRestServiceBearerAuthTest.java
        │               ├── listissuesparameter/
        │               │   ├── JiraIssueParameterDefinitionTest.java
        │               │   └── JiraIssueParameterTest.java
        │               ├── pipeline/
        │               │   ├── CommentStepTest.java
        │               │   ├── IssueFieldUpdateStepTest.java
        │               │   ├── IssueSelectorStepTest.java
        │               │   └── SearchIssuesStepTest.java
        │               ├── selector/
        │               │   ├── DefaultIssueSelectorTest.java
        │               │   ├── ExplicitIssueSelectorTest.java
        │               │   ├── JqlIssueSelectorTest.java
        │               │   └── perforce/
        │               │       ├── JobIssueSelectorTest.java
        │               │       └── P4JobIssueSelectorTest.java
        │               └── versionparameter/
        │                   ├── JiraReleaseVersionParameterTest.java
        │                   ├── JiraVersionParameterDefinitionTest.java
        │                   └── VersionComparatorTest.java
        └── resources/
            ├── hudson/
            │   └── plugins/
            │       └── jira/
            │           ├── JiraBuildActionTest/
            │           │   └── binaryCompatibility/
            │           │       ├── config.xml
            │           │       └── jobs/
            │           │           └── project/
            │           │               ├── builds/
            │           │               │   └── 2/
            │           │               │       └── build.xml
            │           │               └── config.xml
            │           ├── multiple-sites.yml
            │           ├── oldJiraProjectProperty.xml
            │           └── single-site.yml
            └── jira.properties

================================================
FILE CONTENTS
================================================

================================================
FILE: .git-blame-ignore-revs
================================================
# .git-blame-ignore-revs
# Reformatting of code with Spotless
969d12b2b997f23561af51530f9394e8ca34dfd7


================================================
FILE: .github/CODEOWNERS
================================================
* @jenkinsci/jira-plugin-developers


================================================
FILE: .github/FUNDING.yml
================================================
# These are supported funding model platforms

github: [ olamy, rantoniuk]
patreon: # Replace with a single Patreon username
open_collective: # Replace with a single Open Collective username
ko_fi: # Replace with a single Ko-fi username
tidelift: # Replace with a single Tidelift platform-name/package-name e.g., npm/babel
community_bridge: # Replace with a single Community Bridge project-name e.g., cloud-foundry
liberapay: # Replace with a single Liberapay username
issuehunt: # Replace with a single IssueHunt username
otechie: # Replace with a single Otechie username
custom: # Replace with up to 4 custom sponsorship URLs e.g., ['link1', 'link2']


================================================
FILE: .github/ISSUE_TEMPLATE/1-report-bug.yml
================================================
name: "🐛 Bug report"
type: "Bug"
description: Create a bug report to help us improve

body:
  - type: markdown
    attributes:
      value: |
        **Never report security issues on GitHub or other public channels (Gitter/Twitter/etc.)**
        Follow these instruction to report security issues: https://www.jenkins.io/security/#reporting-vulnerabilities

  - type: textarea
    attributes:
      label: Jenkins and plugins versions report
      description: |
        For easier bug reporting, you can get the full list of plugins with this Groovy script that you can run in **Jenkins > Manage Jenkins > Script Console**:
        ```groovy
        println("Jenkins: ${Jenkins.instance.getVersion()}")
        println("OS: ${System.getProperty('os.name')} - ${System.getProperty('os.version')}")
        println "---"

        Jenkins.instance.pluginManager.plugins
          .collect()
          .sort { it.getShortName() }
          .each {
            plugin -> println("${plugin.getShortName()}:${plugin.getVersion()}")
          }
        return
        ```
      placeholder: |
        Jenkins: 2.326
        OS: Linux - 3.10.0-1160.45.1.el7.x86_64
        ---
        ace-editor:1.1
        ant:1.13
        antisamy-markup-formatter:2.5
        apache-httpcomponents-client-4-api:4.5.13-1.0
        authentication-tokens:1.4
        bootstrap4-api:4.6.0-3
        bootstrap5-api:5.1.3-4
        bouncycastle-api:2.25
        ...
      value: |
        <details>
          <summary>Environment</summary>

          <!-- Paste your environment details below -->
          ```text
          Paste the output here
          ```

        </details>
    validations:
      required: true

  - type: textarea
    attributes:
      label: What Operating System are you using (both controller, and any agents involved in the problem)?
    validations:
      required: true

  - type: textarea
    attributes:
      label: Reproduction steps
      description: |
        Write bullet-point reproduction steps.
        Be explicit about any relevant configuration, jobs, build history, user accounts, etc., redacting confidential information as needed.
        The best reproduction steps start with a clean Jenkins install, perhaps a `docker run` command if possible.
        Use screenshots where appropriate, copy textual output otherwise. When in doubt, do both.
        Include relevant logs, debug if needed - https://www.jenkins.io/doc/book/system-administration/viewing-logs/
      placeholder: |
        1. Step 1: ...
        2. Step 2: ...
    validations:
      required: true

  - type: textarea
    attributes:
      label: Expected Results
      description: What was your expected result?
    validations:
      required: true

  - type: textarea
    attributes:
      label: Actual Results
      description: What was the actual result?
    validations:
      required: true

  - type: textarea
    attributes:
      label: Anything else?
      description: You can provide additional context below.


================================================
FILE: .github/ISSUE_TEMPLATE/2-feature-request.yml
================================================
name: "🚀 Feature request"
type: "feature"
description: I have a suggestion

body:
  - type: textarea
    attributes:
      label: What feature do you want to see added?
      description: A clear and concise description of your feature request.
    validations:
      required: true

  - type: textarea
    attributes:
      label: Upstream changes
      description: Link here any upstream changes that might be relevant to this request


================================================
FILE: .github/ISSUE_TEMPLATE/3-documentation.yml
================================================
name: "📝 Documentation"
labels: ["documentation"]
description: "Let us know if any documentation is missing or could be improved"

body:
  - type: textarea
    attributes:
      label: Describe your use-case which is not covered by existing documentation.
      description: If it is easier to submit a documentation patch instead of writing an issue, just do it!
    validations:
      required: true

  - type: textarea
    attributes:
      label: Reference any relevant documentation, other materials or issues/pull requests that can be used for inspiration.


================================================
FILE: .github/ISSUE_TEMPLATE/config.yml
================================================
blank_issues_enabled: true
contact_links:
  - name: Community forum
    url: https://community.jenkins.io/
    about: Please ask and answer questions here
  - name: Mailing lists
    url: https://www.jenkins.io/mailing-lists/
    about: You can also raise a question in one of the user or developer mailing lists


================================================
FILE: .github/pull_request_template.md
================================================
<!--
Put an `x` into the [ ] to show you have filled the information
-->

### Related issue

<!-- Paste links to the issues that are related/resolved by this PR -->
<!-- If this PR is related to upstream libraries/API changes, include those links as well -->

### Changes

<!-- Describe changes: include any relevant information. If you have renamed any files or classes, state the reason to help the reviewer understand the context. -->

### Tests

<!-- Describe how did you test your changes. If you don't have a Jira Cloud instance to test on, ask the maintainer to grant access to https://jenkins-jira-plugin.atlassian.net/ --> 

- [ ] I have updated/added relevant documentation in the `docs/` directory
- [ ] I have verified that the Code Coverage is not lower than before / that all the changes are covered as needed
- [ ] I have tested my changes with a Jira Cloud / Jira Server

<!-- provide here the flavor (Jira Cloud / Jira Server) and the version -->
 

================================================
FILE: .github/release-drafter.yml
================================================
_extends: github:jenkinsci/.github:/.github/release-drafter.yml
name-template: $RESOLVED_VERSION
tag-template: jira-$RESOLVED_VERSION

version-resolver:
  major:
    labels:
      - 'major'
      - 'breaking'
  minor:
    labels:
      - 'minor'
      - 'dependencies'
  patch:
    labels:
      - 'bugfix'
      - 'patch'
  default: minor


================================================
FILE: .github/renovate.json
================================================
{
  "$schema": "https://docs.renovatebot.com/renovate-schema.json",
  "extends": [
    "github>jenkinsci/renovate-config"
  ],
  "packageRules": [
    {
      "matchManagers": ["maven"],
      "matchPackageNames": [
        "io.atlassian.fugue:fugue"
      ],
      "enabled": false
    },
    {
      "matchManagers": ["maven"],
      "groupName": "atlassian",
      "matchPackageNames": [
        "/^com\.atlassian\.plugins:.*$/",
        "/^com\.atlassian\.jira:.*$/",
        "/^io\.atlassian\.util\.concurrent:.*$/"
      ]
    },
    {
      "matchManagers": ["maven"],
      "groupName": "jenkins",
      "matchPackageNames": [
        "/^io\.jenkins\.tools\.bom:.*$/",
        "/^org\.jenkins-ci\.plugins:plugin$/"
      ]
    }
  ]
}


================================================
FILE: .github/workflows/crowdin.yml
================================================
---
name: Crowdin

on:
  push:
    branches:
      - master
  workflow_dispatch:

permissions:
  actions: write
  contents: write
  pull-requests: write

jobs:
  synchronize-with-crowdin:
    runs-on: ubuntu-latest

    steps:

      - name: Checkout
        uses: actions/checkout@v6

      - name: crowdin action
        uses: crowdin/github-action@v2
        with:
          upload_translations: true
          download_translations: true
          skip_untranslated_files: true
          auto_approve_imported: true
          push_translations: true
          export_only_approved: true
          commit_message: 'New Crowdin translations'
          create_pull_request: true
          pull_request_title: 'Update localization'
          pull_request_labels: 'localization'
          base_url: 'https://jenkins.crowdin.com'
          config: 'crowdin.yml'
        env:
          GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
          CROWDIN_PROJECT_ID:  35
          CROWDIN_PERSONAL_TOKEN: ${{ secrets.CROWDIN_PERSONAL_TOKEN }}


================================================
FILE: .github/workflows/jenkins-security-scan.yml
================================================
name: Jenkins Security Scan

on:
  push:
    branches:
      - master
  pull_request:
    types: [ opened, synchronize, reopened ]
  workflow_dispatch:

permissions:
  security-events: write
  contents: read
  actions: read

jobs:
  security-scan:
    uses: jenkins-infra/jenkins-security-scan/.github/workflows/jenkins-security-scan.yaml@v2
    with:
      java-cache: 'maven' # Optionally enable use of a build dependency cache. Specify 'maven' or 'gradle' as appropriate.
      # java-version: 21 # Optionally specify what version of Java to set up for the build, or remove to use a recent default.


================================================
FILE: .github/workflows/release-drafter.yml
================================================
name: Release Drafter
on:
  push:
    branches:
      - master
jobs:
  update_release_draft:
    runs-on: ubuntu-latest
    steps:
      - uses: release-drafter/release-drafter@v7
        with:
          token: ${{ secrets.GITHUB_TOKEN }}


================================================
FILE: .github/workflows/sonarcloud.yml
================================================
name: SonarCloud analysis

on:
  push:
    branches: [ "master" ]
    tags:
      - 'jira*'
  pull_request:
    branches: [ "master" ]
  workflow_dispatch:

permissions:
  pull-requests: read 

jobs:
  Analysis:
    runs-on: ubuntu-latest

    steps:
      - name: Checkout Code
        uses: actions/checkout@v6
        with:
          fetch-depth: 0
          persist-credentials: false

      - uses: actions/setup-java@v5
        with:
          java-version: '21'
          distribution: 'corretto'
          cache: 'maven'

      - name: Run the Maven verify phase
        env:
          SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }}
        run: >
           mvn --batch-mode -Penable-jacoco
           -Dsonar.organization=jenkinsci
           -Dsonar.projectKey=jenkinsci_jira-plugin
           -Dsonar.qualitygate.wait
           test jacoco:report org.sonarsource.scanner.maven:sonar-maven-plugin:5.5.0.6356:sonar



================================================
FILE: .gitignore
================================================
.classpath
.project
.settings
.factorypath
build
target
bin
work/
.work
.env*
.docker
*.code-workspace

# ignore all Idea files except for common codestyle settings
.DS_Store
*.iml
.vscode/
.idea/*

atlassian-ide-plugin.xml


================================================
FILE: .mvn/extensions.xml
================================================
<extensions xmlns="http://maven.apache.org/EXTENSIONS/1.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/EXTENSIONS/1.0.0 http://maven.apache.org/xsd/core-extensions-1.0.0.xsd">
  <extension>
    <groupId>io.jenkins.tools.incrementals</groupId>
    <artifactId>git-changelist-maven-extension</artifactId>
    <version>1.13</version>
  </extension>
</extensions>


================================================
FILE: .mvn/maven.config
================================================
-Pconsume-incrementals
-Pmight-produce-incrementals


================================================
FILE: .pre-commit-config.yaml
================================================
repos:
  - repo: https://github.com/pre-commit/pre-commit-hooks
    rev: v4.6.0
    hooks:
      - id: check-yaml
      - id: check-added-large-files
  - repo: https://github.com/ORCID/pre-commit-spotless
    rev: v1.0.0
    hooks:
      - id: spotless-check
        types_or: [java]
      - id: spotless-apply
        types_or: [java]


================================================
FILE: CONTRIBUTING.md
================================================
# Contribution guidelines

General rules:

- check the [general Jenkins development guide](https://www.jenkins.io/doc/developer/book/)
- make sure to provide tests
- when adding new fields, make sure to [include backward-compatibility](https://www.jenkins.io/doc/developer/persistence/backward-compatibility/) and tests for that
- mark the Pull Request as _draft_ initially, to make sure all the checks pass correctly, then convert it to non-draft.

## Setting up your environment

### Install pre-commit hooks

The [pre-commit](https://pre-commit.com/#install) hooks run various checks to make sure no unwanted files are committed and that the submitted change follows the code style and formatting rules:

```sh
brew install pre-commit && pre-commit install --install-hooks
```

## Notes for maintainers

### Local testing

Use [docker-compose](./docker-compose.yml) to run a local Jenkins instance with the plugin installed. The configuration includes local volumes for both: Jenkins and ssh-agent, so you can easily test the plugin in a clean environment.


### Atlassian sources import

To resolve [some binary compatibility issues](https://github.com/jenkinsci/jira-plugin/pull/140),
the sources from the artifact [com.atlassian.httpclient:atlassian-httpclient-plugin:0.23](https://packages.atlassian.com/maven-external/com/atlassian/httpclient/atlassian-httpclient-plugin/0.23.0/)
has been imported in the project to have control over http(s) protocol transport layer.
The downloaded sources didn't have any license headers but based on the [pom](https://packages.atlassian.com/maven-external/com/atlassian/httpclient/atlassian-httpclient-plugin/0.23.0/atlassian-httpclient-plugin-0.23.0.pom)
sources are Apache License (see pom in src/main/resources/atlassian-httpclient-plugin-0.23.0.pom)

### Testing

There is a [Jira Cloud](https://jenkins-jira-plugin.atlassian.net/) test instance that the changes can be tested against, official maintainers are admins that can grant access for testing to PR submitters on a need-to-have basis.

### Releasing the plugin

See [releasing Jenkins plugins](https://www.jenkins.io/doc/developer/publishing/releasing-manually/).


================================================
FILE: Jenkinsfile
================================================
/*
 See the documentation for more options:
 https://github.com/jenkins-infra/pipeline-library/
*/
buildPlugin(
  forkCount: '1C', // run this number of tests in parallel for faster feedback.  If the number terminates with a 'C', the value will be multiplied by the number of available CPU cores
  useContainerAgent: true, // Set to `false` if you need to use Docker for containerized tests
  configurations: [
    [platform: 'linux', jdk: 25],
    [platform: 'windows', jdk: 21],
])


================================================
FILE: LICENSE.md
================================================
The MIT License

Copyright (c) 2007, Kohsuke Kawaguchi and jira-plugin contributors

Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.



================================================
FILE: README.md
================================================
# Jenkins Jira Plugin

[![Jenkins Version](https://img.shields.io/badge/Jenkins-2.479.3-green.svg?label=min.%20Jenkins)](https://jenkins.io/download/)
[![Jenkins Plugin Installs](https://img.shields.io/jenkins/plugin/i/jira.svg?color=blue)](https://stats.jenkins.io/pluginversions/jira.html)
[![GitHub release](https://img.shields.io/github/release/jenkinsci/jira-plugin.svg?label=Release)](https://github.com/jenkinsci/jira-plugin/releases/latest)
[![Jenkins CI](https://ci.jenkins.io/buildStatus/icon?job=Plugins/jira-plugin/master)](https://ci.jenkins.io/job/Plugins/job/jira-plugin/)
[![Contributors](https://img.shields.io/github/contributors/jenkinsci/jira-plugin.svg)](https://github.com/jenkinsci/jira-plugin/graphs/contributors)
[![Bugs](https://sonarcloud.io/api/project_badges/measure?project=jenkinsci_jira-plugin&metric=bugs)](https://sonarcloud.io/summary/new_code?id=jenkinsci_jira-plugin)
[![Vulnerabilities](https://sonarcloud.io/api/project_badges/measure?project=jenkinsci_jira-plugin&metric=vulnerabilities)](https://sonarcloud.io/summary/new_code?id=jenkinsci_jira-plugin)
[![Coverage](https://sonarcloud.io/api/project_badges/measure?project=jenkinsci_jira-plugin&metric=coverage)](https://sonarcloud.io/summary/new_code?id=jenkinsci_jira-plugin)
[![Quality Gate Status](https://sonarcloud.io/api/project_badges/measure?project=jenkinsci_jira-plugin&metric=alert_status)](https://sonarcloud.io/summary/new_code?id=jenkinsci_jira-plugin)

1. See user documentation at [https://jenkinsci.github.io/jira-plugin/](https://jenkinsci.github.io/jira-plugin/).
1. Use [Declarative pipelines](https://www.jenkins.io/doc/book/pipeline/#declarative-versus-scripted-pipeline-syntax).
1. Check [jira plugin steps reference](https://www.jenkins.io/doc/pipeline/steps/jira/).

## i18n


[![da translation](https://img.shields.io/badge/dynamic/json?color=blue&label=da&style=flat&logo=crowdin&query=%24.progress.0.data.translationProgress&url=https%3A%2F%2Fbadges.awesome-crowdin.com%2Fstats-200016380-35.json)](https://jenkins.crowdin.com/jira-plugin)
[![de translation](https://img.shields.io/badge/dynamic/json?color=blue&label=de&style=flat&logo=crowdin&query=%24.progress.1.data.translationProgress&url=https%3A%2F%2Fbadges.awesome-crowdin.com%2Fstats-200016380-35.json)](https://jenkins.crowdin.com/jira-plugin)
[![en translation](https://img.shields.io/badge/dynamic/json?color=blue&label=en&style=flat&logo=crowdin&query=%24.progress.2.data.translationProgress&url=https%3A%2F%2Fbadges.awesome-crowdin.com%2Fstats-200016380-35.json)](https://jenkins.crowdin.com/jira-plugin)
[![es translation](https://img.shields.io/badge/dynamic/json?color=blue&label=es&style=flat&logo=crowdin&query=%24.progress.3.data.translationProgress&url=https%3A%2F%2Fbadges.awesome-crowdin.com%2Fstats-200016380-35.json)](https://jenkins.crowdin.com/jira-plugin)
[![fr translation](https://img.shields.io/badge/dynamic/json?color=blue&label=fr&style=flat&logo=crowdin&query=%24.progress.4.data.translationProgress&url=https%3A%2F%2Fbadges.awesome-crowdin.com%2Fstats-200016380-35.json)](https://jenkins.crowdin.com/jira-plugin)
[![it translation](https://img.shields.io/badge/dynamic/json?color=blue&label=it&style=flat&logo=crowdin&query=%24.progress.5.data.translationProgress&url=https%3A%2F%2Fbadges.awesome-crowdin.com%2Fstats-200016380-35.json)](https://jenkins.crowdin.com/jira-plugin)
[![ja translation](https://img.shields.io/badge/dynamic/json?color=blue&label=ja&style=flat&logo=crowdin&query=%24.progress.6.data.translationProgress&url=https%3A%2F%2Fbadges.awesome-crowdin.com%2Fstats-200016380-35.json)](https://jenkins.crowdin.com/jira-plugin)
[![pl translation](https://img.shields.io/badge/dynamic/json?color=blue&label=pl&style=flat&logo=crowdin&query=%24.progress.7.data.translationProgress&url=https%3A%2F%2Fbadges.awesome-crowdin.com%2Fstats-200016380-35.json)](https://jenkins.crowdin.com/jira-plugin)

This plugin uses [CrowdIn platform](https://jenkins.crowdin.com/jira-plugin) as the frontend to manage translations. If you would like to contribute translation of this plugin in your language,  you're most welcome! For details, see [jenkins.io CrowdIn introduction](https://www.jenkins.io/doc/developer/crowdin/translating-plugins/).



================================================
FILE: crowdin.yml
================================================
---

files:
  - source: '/src/main/resources/hudson/plugins/jira/**/*.properties'
    ignore:
      - '/src/main/resources/hudson/plugins/jira/**/%file_name%_%two_letters_code%.properties'
    translation: '/src/main/resources/hudson/plugins/jira/**/%file_name%_%two_letters_code%.properties'
    escape_quotes: 0
    escape_special_characters: 0

project_id_env: CROWDIN_PROJECT_ID
api_token_env: CROWDIN_PERSONAL_TOKEN


================================================
FILE: docker-compose.yml
================================================
#  docker compose up -d --build --force-recreate
services:
    jenkins:
        image: jenkins/jenkins:lts
        restart: on-failure
        hostname: jenkins
        ports:
            - "8080:8080"
            - "50000:50000"
        volumes:
            - .docker/jenkins-data:/var/jenkins_home:rw
            - ./casc.d:/var/jenkins_home/casc.d/:ro
            # Mounting the ssh private key as "container secret" makes it available in JCasc as the variable ${SSH_AGENT_KEY}
            - ./secrets/id_jenkins.pem:/run/secrets/SSH_AGENT_KEY:ro
        environment:
            - JENKINS_EXT_URL=http://localhost:8080
            - CASC_JENKINS_CONFIG=/var/jenkins_home/casc.d/
            # - org.jenkinsci.plugins.durabletask.BourneShellScript.LAUNCH_DIAGNOSTICS=true
            # - JENKINS_OPTS=-Djenkins.install.runSetupWizard=false
    jenkins-agent:
        image: jenkins/ssh-agent:latest-jdk21
        restart: on-failure
        hostname: agent
        #privileged: true
        depends_on: 
            - jenkins
        volumes:
            - .docker/jenkins-agent-data:/home/jenkins:rw
            # - /var/run/docker.sock:/var/run/docker.sock:rw
        environment:
            - JENKINS_AGENT_SSH_PUBKEY=ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIBpNqXQ4x7fPPUBbYPxKF77Zqq6d35iPCD2chg644OUD noreply@jenkinsagent.local

volumes:
    jenkins-data:
    jenkins-agent-data:


================================================
FILE: docs/.nojekyll
================================================


================================================
FILE: docs/README.md
================================================
# Jenkins Jira plugin

This plugin integrates with Jenkins the [Atlassian Jira Software](http://www.atlassian.com/software/jira/) (both Cloud and Server versions). 

## Configuration

!> **Jira Cloud** does not support Bearer Authentication

To integrate Jenkins with Atlassian Jira Cloud, you need to use an API token as a _service user_. Jira Cloud requires an email address for all users, so you cannot create a user without one.

### Steps

1. **Create an API Token**

    Follow the [Atlassian API tokens documentation](https://confluence.atlassian.com/cloud/api-tokens-938839638.html) to generate a new API token.

2. **Add a Global Jenkins Credential**

    - **Username:** Your Atlassian ID email address
    - **Password:** The API token you created

3. **Test Your API Token**

    Verify your API token by running the following command (replace `<email>`, `<API token>`, `<YourCloudInstanceName>`, and `TEST-1` with your details):

    ```bash
    curl -X GET -u <email>:<API token> -H "Content-Type: application/json" \
      https://<YourCloudInstanceName>.atlassian.net/rest/api/latest/issue/TEST-1
    ```

    A successful response returns the issue details in JSON format.

4. **Check for CAPTCHA**

    Ensure that CAPTCHA is **not** triggered for your user, as this will prevent the API token from working. For more information, see the [CAPTCHA section in Atlassian REST API documentation](https://developer.atlassian.com/cloud/jira/platform/jira-rest-api-basic-authentication/).

5. **Test Connection**
    
    Finally, use the **Validate Settings** button on the plugin configuration page, to see if it can connect to the Jira instance.

![plugin-configuration](images/Plugin_Configuration.png)


## Something doesn't work?

First, check [Github Issues](https://github.com/jenkinsci/jira-plugin/issues) for already reported bugs.

Then, Contribute or Sponsor!

We all love Open Source, but... Open Source Software relies on contributions of fellow developers. Please contribute by [opening Pull Requests](#contributing) or if you are not a developer, consider sponsoring one of the maintainers - see ["Sponsor this project" section.](https://github.com/jenkinsci/jira-plugin)

================================================
FILE: docs/_sidebar.md
================================================
* [Home](/)
* [Features](features.md)
* [System Properties](system-properties.md)
* [Usage Examples](usage-examples.md)
* [Troubleshooting](troubleshooting.md)
* [Changelog](changelog.md)


================================================
FILE: docs/changelog.md
================================================
Changelog
===

### Newer versions

See [GitHub releases](https://github.com/jenkinsci/jira-plugin/releases)

### Unreleased

Release date:  _March 2, 2020_

* Changed all references of JIRA to Jira per [Atlassian branding updates](https://community.atlassian.com/t5/Feedback-Forum-articles/A-new-look-for-Atlassian/ba-p/638077)
* JiraCreateIssueNotifier: regard all statuses in "done" category as finished

### 3.0.11

Release date:  _Nov 21, 2019_

* Fix security issue

### 3.0.10

Release date:  _Sep 26, 2019_

* dependencies cleanup (remove dependency on org.codehaus.jackson:*)

### 3.0.9

Release date:  _Aug 21, 2019_

* JENKINS-59001 IssueSelectorStep should handle NullPointerException caused by having no configured sites
* JENKINS-57899 Jira site configuration lost after a restart

### 3.0.8

Release date:  _Jun 28, 2019_

* JENKINS-58244 JIRA Site at folder level doesn't show credentials for non-admin users
* JENKINS-57664 On Release of a Version recieve a Null Pointer exception

### 3.0.7

Release date:  _May 1, 2019_

* JENKINS-56951 JIRA plugin config incorrectly mixed with properties section
* JENKINS-52906 jira-plugin: FAILED TO EXPORT hudson.plugins.jira.JiraProjectProperty
* JENKINS-33222 Concurrent builds are blocking with jira-plugin
* JENKINS-19195 Add description field to Release JIRA version action

### 3.0.6

Release date:  _March 30, 2019_

* JENKINS-56810 Add current date in startDate when creating new version 
* JENKINS-56697 Simplify constructor, main URL is the only mandatory field 
* JENKINS-50643 Jira Plugin v2.4.2 leaks selectors resulting in Too Many Open Files

## 3.0.5

Release date:  _Jul 7, 2018_

* JENKINS-54469 Unable to set Thread Executor Size when configuring Jira Plugin 
* JENKINS-54131 "Failed to parse changelog" in JIRA plugin 3.0.3 
* JENKINS-54116 Jenkins Jira Plugin - Unable to add version
 
### 3.0.4

Release date:  _Oct 26, 2018_

* JENKINS-54144 Job fails as JiraSCMListsener/JiraSite potentially creating Executor with 0 threads

### 3.0.3

Release date:  _Oct 16, 2018_

* JENKINS-54042 Fix some misconfiguration between connect time and read timeout
* JENKINS-53808 Binary compatibility broken between JIRA plugin 3.0.2 and Artifactory plugin 2.16.2
* JENKINS-53642 Configuration for "Add timestamp to JIRA comments" not observed/remembered

### 3.0.2

Release date:  _Sep 25, 2018_

* SECURITY-1029 - CSRF vulnerability and missing permission checks in Jira Plugin allowed capturing credentials

### 3.0.1

Release date:  _Aug 22, 2018_

* JENKINS-54093 Jenkins Jira Plugin sets connection timeout to default = 10 after Jenkins restart
* JENKINS-53150 Remove Perforce Plugin dependency
* JENKINS-51164 JIRA plugin doesn't honor proxy excludes
* JENKINS-45789 Use Credentials Plugin for JIRA Global Configuration User

### 3.0.0

Release date:  _May 20, 2018_

* JENKINS-51312 Jira plugin core 2.60.1
* JENKINS-51310 Update JIRA plugin to use jackson2-api-plugin

### 2.5.2

Release date:  _May 4, 2018_

* JENKINS-49975 BasicHttpCache error with JIRA Plugin 2.5.1
* JENKINS-49231 jira-plugin 2.5.1 throws exception fails build
* JENKINS-48357 Binary Compatibility between JIRA Plugin and Apache HttpComponents Client 4.x API
* JENKINS-25829 Proxy configuration does not work

### 2.4.2

Release date:  _Aug 8, 2017_

* JENKINS-45992 Cannot validate JIRA site settings

### Version 2.4

Release date:  _Aug 3, 2017_

* JENKINS-44524 Support adding JIRA sites on folder

### 2.3.1

Release date:  _May 23, 2017_

* JENKINS-40571 JiraVersionCreatorBuilder fields missing in post-build form

### 2.3

Release date:  _Dec 19, 2016_

* JENKINS-39192 Support for updating custom fields 
* JENKINS-39091 Jira plugin fails to log in to Jira site after dependency updates 
* JENKINS-38142 Possibility to specify JIRA site in jenkins pipeline project 
* JENKINS-36726 Plugin comments on subsequent successful builds 
* JENKINS-35998 No issue update if at least one issue does not exists 
* JENKINS-34661 Bump LTS to 1.642.3 
* JENKINS-33996 Issue selector step improvement 
* JENKINS-33859 NPE when well-formed Jira Issue doesn't exist 
* JENKINS-32602 jira-plugin missing License 
* JENKINS-32492 Rename all dropdown labels to include JIRA: prefix 
* JENKINS-32491 Rename Workflow Plugin to Pipeline 
* JENKINS-31164 Issue Type must be selectable from fetched dropdown 
* JENKINS-24207 Use Perforce Jobs attached to changelist to track JIRA issues 
* JENKINS-19286 Support multiple fix versions

### 2.2.1

Release date:  _Mar 26, 2016_

* JENKINS-33293 (Jira) Updater throws NullPointerException for labels
* JENKINS-33211 NullPointerException in JiraVersionParameterValue.java

### 2.2

Release date:  _Feb 20, 2016_

* Split each SCM changes in paragraphs
* support release candidates (RCs) via Maven ComparableVersion
* Console logging improvements in various places
* JiraEnvironmentVariableBuilder support
* Support adding labels to updated issues
* (optionally) add scm entry change date and time to description in JIRA tickets
* JENKINS-32504 Make JiraEnvironmentVariableBuilder compatible with pipeline
* JENKINS-32276 JIRA Release Version Parameter is truncating list of Jira versions
* JENKINS-32170 Support CLI parameter submission for JiraIssueParameterDefinition
* JENKINS-32106 Issue type "UNKNOWN" in Release Notes
* JENKINS-31268 @Exported returns double XML value for getter
* JENKINS-31113 Configurable HTTP timeout parameter for JiraRestService

### 2.1

Release date:  _Now 18, 2015_

* Bumped Jenkins Core to LTS v. 1.609.3
* Added dependencies: mailer-plugin, matrix-plugin
* Removed dependencies: maven-plugin
* JENKINS-32949 Issue with JIRA plugins in JENKINS 
* JENKINS-31626 Expand JIRA Project Key variable in other build tasks 
* JENKINS-31349 Jira configuration - Validate Settings doesn't validate username/password 
* JENKINS-30829 JIRA Generate Release Notes needs default Environment Variable 
* JENKINS-30305 Allow CLI parameter submission for JiraVersionParameterDefinition 
* JENKINS-26701 Jira Plugin: I need sorting option in "JIRA Release Version Parameter". Is it possible? 
* JENKINS-25828 JIRA version name/value not picked up by remote API 
* JENKINS-17156 If Updater fails to update due to missing permission, it crashes and never flushes the comment queue 
* JENKINS-13436 Message logged by JIRA plugin should mention that the message relates to a Jenkins job. 
* JENKINS-12578 Jira issue parameter value is not exposed via remote API 
* JENKINS-3709 Jira login information should be scrambled in the configuration file

### 2.0.3

Release date:  _Oct 26, 2015_

* JENKINS-30682 Ticket creation fails when no components in JIRA project exist / JIRA rejects empty component list
* JENKINS-30408 JIRA REST API requests lead to 404 (not found) 
* JENKINS-30333 Thread Leak due to use of deprecated JiraSize.createSession

### 2.0.1

Release date:  _Sep 10, 2015_

* JENKINS-30242 Update to 1.13.2 breaks global configuration submission when jira-plugin installed

### 2.0

Release date:  _Sep 2, 2015_

* switch from JIRA RPC SOAP to JIRA REST API communication - the former has been deprecated and dropped since JIRA v.7.0.
* JENKINS-23257 Non well-formed response from JIRA error is hard to diagnose 
* JENKINS-18227 Add support for Atlassian OnDemand JIRA 
* JENKINS-18166 Add support for JIRA REST API - JIRA SOAP API will be removed in JIRA 7 
* JENKINS-10223 This is a valid URL but it doesn't look like JIRA

### 1.41

Release date:  _Jun 10, 2015_

* JENKINS-22628 Change comments/description to use String.format() instead. 
* JENKINS-21776 Jenkins jira comment text typo 
* JENKINS-20528 Unable to link to Jira 
* JENKINS-9549 JIRA plugin does not create links to JIRA repository 
* JENKINS-1904 Can't get issue links generated with out user/password

### Version 1.39

Release date:  _Oct 6, 2013_

* Ability only to comment issue without processing of workflow (pull #38)

### 1.38

Release date:  _Aug 23, 2013_

* Post build step to create new JIRA version (pull #30)

### 1.37

Release date:  _Jun 21, 2013_

* Error with empty alternative url issue #18229

### 1.35

Release date:  _Jul 29, 2012_

* Prevents multiple comments on one issue for matrix builds. (PR #13)

### 1.34

Release date:  _Jun 11, 2012_

* Fix NPE when Jenkins user does not have access to perform any workflow actions JENKINS-13998

### 1.33

Release date:  _Jun 1, 2012_

* Support workflow steps as build actions and/or post-build notifiers JENKINS-13652

### 1.32

Release date:  _May 15, 2012_

* Option to show archived versions.

### 1.31

Release date:  _May 1, 2012_

* Add JiraIssueMigrator - a post build action that will move issues to a new fixVersion based on a JQL query.
* Add Additional filtering of issues to be included in the release notes. Defaults to 'status in (Resolved, Closed)'

### 1.30

Release date:  _April 25, 2012_

* Add build parameter that providers a drop-down with JIRA release versions
* Add a build wrapper that will assemble release notes based on issues in the release version and store it in an environment variable
* JENKINS-123 Issue summary
* JENKINS-124 Another Issue summary
* JENKINS-321 Yet another issue summary
* Add a post-build action that will mark a version as released in JIRA

### 1.29

Release date:  _August 25, 2011_

* JENKINS-10817 Jira-plugin should add the overall build result to the issue's comment
* Include revisions also for non-subversion plugins; include revisions also if we don't have a repository browser
* Defined a new parameter type for parameterized builds that allow you to select a JIRA ticket (from the result of a JQL query)

### 1.28

Release date:  _Jun 15, 2011_

* Improve the form validation error check JENKINS-9625
* Supported security level of the comment JENKINS-1489

### 1.27

Release date:  _Feb 27, 2011_

* Updates for Jenkins

### 1.26

Release date:  _Jan 14, 2011_

* JENKINS-2508 : JIRA plugin not updating JIRA when perforce plugin used.

### 1.25

* JENKINS-6758: Failed to save system settings with JIRA Plugin.

### 1.24

* JENKINS-6462: Version 1.355 of Hudson and Jira Plugin 1.21: Images in Jira comments are not showing up.

### Version 1.23

* JENKINS-6264, JENKINS-6282: IndexOutOfBoundsException when no issue pattern is configured (default pattern wasn't used)
* JENKINS-6381: configured patterned wasn't used for changelog annotation. Default pattern was always used for that.
* improved default pattern to not match commit messages with dots in the number part (like 'projectname-1.2.3'). These messages are e.g. used by the Maven release plugin

### Version 1.22

* JENKINS-6043: Issue pattern can be configurable
* JENKINS-6225: option to update jira issue whatever the build result is (even if failed)

### 1.21

* JENKINS-5989: option to record scm changes in jira.
* JENKINS-6007: Added French localization.

### 1.20

* Added Japanese localization (JENKINS-5788)

### 1.19

* Fix: Prevent carrying forward invalid issue ids forever

### 1.18

* Case insensitive matching of JIRA ids also in the 'recent changes' view (JENKINS-4132)
* fetch missing details for JIRA issues - i.e. completes issue title tooltip in 'recent changes' view (JENKINS-5252)
* prevent build FAILURE if JIRA site is not available (JENKINS-3046)

### 1.17

* Fixed an ArrayIndexOutOfBoundsException when JIRA issues contain '$' in the name.
* Support underscore in project names (JENKINS-4092)
* Support digits in project names (JENKINS-729)
* Case insensitive matching of JIRA ids (JENKINS-4132)
* Don't strip JIRA id from posted comment
* German translation

### 1.15

Release date:  _Aug 22, 2008_

* Update JIRA if the build is UNSTABLE or better.  Previously only updated if the build was stable.
* Include relevant SCM comment in the JIRA comment which should make JIRA ticket history more meaningful.

### 1.13

Release date:  _Auh 5, 2008_

* Fixed a performance issue in a large enterprise deployment of JIRA (JENKINS-1703)

### Version 1.12

* A typo in the commit message shouldn't break builds (JENKINS-1593)
* Postpone JIRA updates until a successful build is obtained (JENKINS-506)

### Version 1.11

* Added more logging and debug flag to examine issues that people are reporting (report)

### Version 1.10

* Wiki-style notation option wasn't persisted (JENKINS-977)
* Fixed a packaging problem (JENKINS-1127)

### 1.9

* Fixed NPE when failed to talk to JIRA (JENKINS-1097)

### 1.8

* Be more graceful in dealing with URLs (JENKINS-896)
* URLs need to be escaped (JENKINS-943)

### 1.7

* Fixed NPE when username/password is not set (JENKINS-828)

### 1.6

* Relaxed the JIRA project key regexp a little bit to allow numbers (JENKINS-729)

### 1.5

* Issue hyperlinking is now smart enough not to be confused by strings that look like JIRA issue that actually aren't.

### 1.4

* Fixed a bug that prevented tooltips for JIRA issues from being displayed JENKINS-694


================================================
FILE: docs/features.md
================================================
# Jenkins Jira plugin features

### Using Jira REST API

This plugin has an optional feature to update Jira issues with a back pointer to Jenkins build pages. This allows the submitter and watchers to quickly find out which build they need to pick up to get the fix.

![plugin-configuration](images/Plugin_Configuration.png)

### Jira Issue links in build Changelog

When you configure your Jira site in Jenkins, the plugin will automatically hyperlink all matching issue names to Jira.

If you have additionally provided username/password to Jira, the hyperlinks will also contain tooltips with the issue summary.

![example-annotated-changelog](images/example_annotated_changelog.png)

### Updating Jira issues with back pointers

If you also want to use this feature, you need to supply a valid user id/password. If you need the comment only to be visible to a certain Jira group, e.g. _Software Development_, enter the groupname.

Now you also need to configure jobs. I figured you might not always have write access to the Jira (say you have a Jenkins build for one of the Apache commons project that you depend on), so that's why this is optional.  

The following screen shows how a Jira issue is updated:

![jira-comments](images/Jira_Comments.jpg)

By taking advantages of Jenkins' [fingerprint](https://wiki.jenkins.io/display/JENKINS/Fingerprint) feature, when your other projects that depend on this project pick up a build with a fix, those build numbers can also be recorded in Jira.

This is quite handy when a bug is fixed in one of the libraries, yet the submitter wants a fix in a different project. This happens often in my work, where a bug is reported against JAX-WS but the fix is in JAXB.

For curious mind, see [this thread for how this works behind the scene](http://jenkins.361315.n4.nabble.com/How-can-does-Hudson-Jira-integration-works-td374680.html).

### Referencing Jira Release version

To reference Jira Release versions in your build, you can pull these
releases directly from Jira by adding the Jira Release Version
Parameter.

This can be useful for generating release notes, trigerring
parameterized build, etc.  
![version-parameters](images/version_parameters.png)

### Generating Release Notes

You can also generate release notes to be used during your build. These notes can be retrieved from an environment variable. See the [Maven Project Plugin](https://wiki.jenkins.io/display/JENKINS/Maven+Project+Plugin) for
the environment variables found within the POM.  
![release-notes](images/release_notes.png)

After your build has run, you can also have the plugin mark a release as resolved. This typically will be a release you specified in your Build Parameters.  
![marking-as-resolved](images/mark_as_resolved.png)

The plugin can also move certain issues matching a JQL query to a new release version.  
![moving-issues](images/move_issues.png)

Sample usage of generated Release Notes:
![release-notes-config](images/release_notes_config.png)

### Jira Authentication & Permissions required

**Note:** As a rule of thumb, **you should be always using a service account** (instead of a personal account) to integrate Jenkins with Jira.

Make sure that the Jira user used by Jenkins has enough permissions to execute its actions. You can do that via Jira Permission Helper tool.

- For creating Jira issues, the user has to be able to Create Issues in the specified project
- If you additionally enter assignee or component field values, make sure that:
      - both of the fields are assigned to the corresponding Jira Screen
      - the Jira user is Assignable in the project
      - the Jenkins Jira user can Assign issues


================================================
FILE: docs/index.html
================================================
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>Document</title>
  <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1" />
  <meta name="description" content="Description">
  <meta name="viewport" content="width=device-width, initial-scale=1.0, minimum-scale=1.0">
  <link rel="stylesheet" href="//cdn.jsdelivr.net/npm/docsify@4/lib/themes/buble.css">
</head>
<body>
  <div id="app"></div>
  <script>
    window.$docsify = {
      name: 'Jenkins Jira plugin',
      repo: 'https://github.com/jenkinsci/jira-plugin',
      loadSidebar: true,
    }
  </script>
  <!-- Docsify v4 -->
  <script src="//cdn.jsdelivr.net/npm/docsify@4"></script>
  <script src="//cdn.jsdelivr.net/npm/docsify/lib/plugins/search.min.js"></script>
  <script src="//cdn.jsdelivr.net/npm/docsify/lib/plugins/zoom-image.min.js"></script>
  <script src="//cdn.jsdelivr.net/npm/prismjs/components/prism-groovy.min.js"></script>
</body>
</html>


================================================
FILE: docs/system-properties.md
================================================
# System Properties

There are some cases when you might want to change the plugin's behavior globally, by overriding [Jenkins system properties](https://www.jenkins.io/doc/book/managing/system-properties/). 

This plugin provides the following additional settings, that are not available via UI:

- `-Dhudson.plugins.jira.JiraMailAddressResolver.disabled=true`
    Use to disable resolving user email from Jira usernames. 


================================================
FILE: docs/troubleshooting.md
================================================
# Common issues

## Adding a custom Log Recorder

To help debug any issues with this plugin, it's useful to look at more detailed logs. To enable them, create a [custom Log Recorder](https://www.jenkins.io/doc/book/system-administration/viewing-logs/#logs-in-jenkins) for Logger `hudson.plugins.jira` and Log Level `FINE`. 

## Jenkins <---> Jira SSL connectivity problems

If you encounter stacktrace like this:

```stacktrace
Caused by: javax.net.ssl.SSLHandshakeException: sun.security.validator.ValidatorException: PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException: unable to find valid certification path to requested target
```

make sure the JRE/JDK that Jenkins master is running (or the Jenkins slaves are running) contain the valid CA chain certificates that Jira is running with.
You can test it using this [SSLPoke.java class](https://gist.github.com/warden/e4ef13ea60f24d458405613be4ddbc51):

```sh
$ wget -O SSLPoke.java https://gist.githubusercontent.com/warden/e4ef13ea60f24d458405613be4ddbc51/raw/7f258a30be4ddea7b67239b40ae305f6a2e98e0a/SSLPoke.java

$ /usr/java/jdk1.8.0_131/bin/javac SSLPoke.java

$ /usr/java/jdk1.8.0_131/jre/bin/java SSLPoke jira.domain.com 443
Successfully connected
```

References:

- [Jenkins fails with PKIX Path building error](https://stackoverflow.com/questions/52842214/jenkins-fails-with-pkix-path-building-error)
- [PKIX path building failed error message
](https://support.cloudbees.com/hc/en-us/articles/217078498-PKIX-path-building-failed-error-message)


================================================
FILE: docs/usage-examples.md
================================================
# Usage examples

## jiraCommentIssues usage example

You need keep reference to used scm.
As an example, you can write a flow:

```groovy
node {
    def gitScm = git url: 'git@github.com:jenkinsci/jira-plugin.git', branch: 'master'
    sh 'make something'
    jiraCommentIssues( 
            issueSelector: DefaultSelector(), 
            scm: gitScm)            
    gitScm = null
}
```

Note that a pointer to scm class should be better cleared to not serialize scm object between steps.

You can add some labels to issue in jira:

```groovy
    jiraCommentIssues( 
            issueSelector: DefaultSelector(), 
            scm: gitScm,
            labels: [ "$version", "jenkins" ])            
```

## jiraExecuteWorkflow  usage example

```groovy
node {
    jiraExecuteWorkflow(
            jqlSearch: "project = EX and labels = 'jenkins' and labels = '${version}'",
            workflowActionName: 'Resolve Issue',
            comment: 'comment')
}
```

## jiraCreateReleaseNotes usage example

```groovy
node {
    jiraCreateReleaseNotes(jiraProjectKey: 'TST',
            jiraRelease: '1.1.1', jiraEnvironmentVariable: 'notes', jiraFilter: 'status in (Resolved, Closed)')
            {
                //do some useful here
                //release notes can be found in environment variable jiraEnvironmentVariable
                print env.notes
            }
}
```

## jiraMarkVersionReleased usage example

```groovy
node {
    jiraMarkVersionReleased( 
            jiraProjectKey: 'TEST', 
            jiraRelease: '1.1.1')
}
```

## jiraUpdateIssueField usage example

```groovy
node {
    jiraUpdateIssueField(
            issueSelector: ExplicitSelector("JIRA-123"),
            fieldId: "10001",
            fieldValue: "value"
    )
}
```

## SearchIssuesStep

Custom pipeline step (see [step-api](https://github.com/jenkinsci/workflow-plugin/blob/master/step-api/README.md)) that allow to search by jql query directly from workflow.

usage:

```groovy
node {
    List<String> issueKeys = jiraSearch(jql: "project = EX and labels = 'jenkins' and labels = '${version}'")	
}
```

## CommentStep

Interface for Pipeline job types that simply want to post a comment e.g.:

```groovy
node {
    jiraComment(issueKey: "EX-111", body: "Job '${env.JOB_NAME}' (${env.BUILD_NUMBER}) built. Please go to ${env.BUILD_URL}.")
}
```

## JiraEnvironmentVariableBuilder

Not supported in Pipeline. You can get current jira url (if you are not using the Groovy sandbox):

```groovy
import hudson.plugins.jira.JiraSite;

node {
    String jiraUrl = JiraSite.get(currentBuild.rawBuild).name    	
    env.JIRA_URL = jiraUrl
}
```

To replace JIRA_ISSUES env variable, you can use pipeline step jiraIssueSelector:

```groovy
    List<String> issueKeys = jiraIssueSelector()
```

or if you use custom issue selector:

```groovy
    List<String> issueKeys = jiraIssueSelector(new CustomIssueSelector())
```

## Other features

Some features are currently not supported in pipeline.
If you are adding new features please make sure that they support Jenkins pipeline Plugin.
See [here](https://github.com/jenkinsci/workflow-plugin/blob/master/COMPATIBILITY.md) for some information.
See [here](https://github.com/jenkinsci/workflow-plugin/blob/master/basic-steps/CORE-STEPS.md) for more information how core jenkins steps integrate with workflow jobs.

Running a notifiers is trickier since normally a flow in progress has no status yet, unlike a freestyle project whose status is determined before the notifier is called (never supported).
So notifiers will never be implemented as you can use the catchError step and run jira action manually.
I'm going to create a special pipeline steps to replace this notifiers in future.


================================================
FILE: pom.xml
================================================
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
  <modelVersion>4.0.0</modelVersion>
  <parent>
    <groupId>org.jenkins-ci.plugins</groupId>
    <artifactId>plugin</artifactId>
    <version>6.2138.v03274d462c13</version>
    <relativePath />
  </parent>

  <artifactId>jira</artifactId>
  <version>${revision}${changelist}</version>
  <packaging>hpi</packaging>
  <name>Jenkins Jira plugin</name>
  <description>Integrates Jenkins to Jira</description>
  <url>https://github.com/jenkinsci/${project.artifactId}-plugin</url>

  <licenses>
    <license>
      <name>The MIT license</name>
      <url>https://github.com/jenkinsci/jira-plugin/raw/master/LICENSE.md</url>
      <distribution>repo</distribution>
    </license>
  </licenses>

  <developers>
    <developer>
      <id>olamy</id>
      <name>Olivier Lamy</name>
    </developer>
    <developer>
      <id>warden</id>
      <name>Radek Antoniuk</name>
    </developer>
  </developers>

  <scm>
    <connection>scm:git:https://github.com/${gitHubRepo}.git</connection>
    <developerConnection>scm:git:git@github.com:${gitHubRepo}.git</developerConnection>
    <tag>jira-3.20</tag>
    <url>https://github.com/${gitHubRepo}</url>
  </scm>

  <issueManagement>
    <system>Github</system>
    <url>https://github.com/jenkinsci/jira-plugin/issues</url>
  </issueManagement>

  <properties>
    <revision>3.22</revision>
    <changelist>-SNAPSHOT</changelist>
    <gitHubRepo>jenkinsci/${project.artifactId}-plugin</gitHubRepo>
    <hpi.bundledArtifacts>atlassian-event,atlassian-httpclient-api,atlassian-util-concurrent,fugue,jira-rest-java-client-api,jira-rest-java-client-core,maven-artifact,plexus-utils,sal-api</hpi.bundledArtifacts>
    <hpi.strictBundledArtifacts>true</hpi.strictBundledArtifacts>
    <jira-rest-client.version>6.0.2</jira-rest-client.version>
    <fugue.version>4.7.2</fugue.version>
    <!-- https://www.jenkins.io/doc/developer/plugin-development/choosing-jenkins-baseline/ -->
    <jenkins.baseline>2.492</jenkins.baseline>
    <jenkins.version>${jenkins.baseline}.3</jenkins.version>
    <spotless.check.skip>false</spotless.check.skip>
    <ban-junit4-imports.skip>false</ban-junit4-imports.skip>
    <ban-commons-lang-2.skip>false</ban-commons-lang-2.skip>
  </properties>

  <dependencyManagement>
    <dependencies>
      <dependency>
        <groupId>io.jenkins.tools.bom</groupId>
        <artifactId>bom-${jenkins.baseline}.x</artifactId>
        <version>5473.vb_9533d9e5d88</version>
        <type>pom</type>
        <scope>import</scope>
      </dependency>
      <dependency>
        <groupId>com.atlassian.plugins</groupId>
        <artifactId>atlassian-plugins-core</artifactId>
        <version>8.2.1</version>
      </dependency>
    </dependencies>
  </dependencyManagement>

  <dependencies>
    <dependency>
      <groupId>com.atlassian.jira</groupId>
      <artifactId>jira-rest-java-client-api</artifactId>
      <version>${jira-rest-client.version}</version>
      <exclusions>
        <!-- Deprecated and not needed at runtime -->
        <exclusion>
          <groupId>com.google.code.findbugs</groupId>
          <artifactId>jsr305</artifactId>
        </exclusion>
        <!-- Provided by Jenkins core -->
        <exclusion>
          <groupId>com.google.guava</groupId>
          <artifactId>guava</artifactId>
        </exclusion>
        <!-- Provided by joda-time-api plugin -->
        <exclusion>
          <groupId>joda-time</groupId>
          <artifactId>joda-time</artifactId>
        </exclusion>
      </exclusions>
    </dependency>
    <dependency>
      <groupId>com.atlassian.jira</groupId>
      <artifactId>jira-rest-java-client-core</artifactId>
      <version>${jira-rest-client.version}</version>
      <exclusions>
        <exclusion>
          <groupId>com.atlassian.httpclient</groupId>
          <artifactId>atlassian-httpclient-library</artifactId>
        </exclusion>
        <exclusion>
          <groupId>com.atlassian.httpclient</groupId>
          <artifactId>atlassian-httpclient-plugin</artifactId>
        </exclusion>
        <!-- Deprecated and not needed at runtime -->
        <exclusion>
          <groupId>com.google.code.findbugs</groupId>
          <artifactId>jsr305</artifactId>
        </exclusion>
        <!-- Provided by Jenkins core -->
        <exclusion>
          <groupId>com.google.guava</groupId>
          <artifactId>guava</artifactId>
        </exclusion>
        <exclusion>
          <groupId>commons-codec</groupId>
          <artifactId>commons-codec</artifactId>
        </exclusion>
        <!-- Provided by joda-time-api plugin -->
        <exclusion>
          <groupId>joda-time</groupId>
          <artifactId>joda-time</artifactId>
        </exclusion>
        <!-- Provided by commons-lang3-api plugin -->
        <exclusion>
          <groupId>org.apache.commons</groupId>
          <artifactId>commons-lang3</artifactId>
        </exclusion>
        <!-- Provided by apache-httpcomponents-client-4-api plugin -->
        <exclusion>
          <groupId>org.apache.httpcomponents</groupId>
          <artifactId>httpasyncclient</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.apache.httpcomponents</groupId>
          <artifactId>httpasyncclient-cache</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.apache.httpcomponents</groupId>
          <artifactId>httpclient</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.apache.httpcomponents</groupId>
          <artifactId>httpclient-cache</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.apache.httpcomponents</groupId>
          <artifactId>httpcore</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.apache.httpcomponents</groupId>
          <artifactId>httpcore-nio</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.apache.httpcomponents</groupId>
          <artifactId>httpmime</artifactId>
        </exclusion>
        <!-- Provided by Jersey 2 API plugin -->
        <exclusion>
          <groupId>org.codehaus.jettison</groupId>
          <artifactId>jettison</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.glassfish.jersey.core</groupId>
          <artifactId>jersey-client</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.glassfish.jersey.core</groupId>
          <artifactId>jersey-common</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.glassfish.jersey.media</groupId>
          <artifactId>jersey-media-jaxb</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.glassfish.jersey.media</groupId>
          <artifactId>jersey-media-json-jettison</artifactId>
        </exclusion>
        <!-- Provided by Jenkins core -->
        <exclusion>
          <groupId>org.slf4j</groupId>
          <artifactId>slf4j-api</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.springframework</groupId>
          <artifactId>spring-beans</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.springframework</groupId>
          <artifactId>spring-core</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.springframework</groupId>
          <artifactId>spring-jcl</artifactId>
        </exclusion>
      </exclusions>
    </dependency>
    <dependency>
      <groupId>io.atlassian.fugue</groupId>
      <artifactId>fugue</artifactId>
      <version>${fugue.version}</version>
    </dependency>
    <dependency>
      <groupId>io.atlassian.util.concurrent</groupId>
      <artifactId>atlassian-util-concurrent</artifactId>
      <version>4.1.0</version>
    </dependency>
    <dependency>
      <groupId>io.jenkins.plugins</groupId>
      <artifactId>caffeine-api</artifactId>
    </dependency>
    <dependency>
      <groupId>io.jenkins.plugins</groupId>
      <artifactId>commons-collections4-api</artifactId>
      <version>4.5.0-8.va_d5448ef9011</version>
    </dependency>
    <dependency>
      <groupId>io.jenkins.plugins</groupId>
      <artifactId>commons-lang3-api</artifactId>
    </dependency>
    <dependency>
      <groupId>io.jenkins.plugins</groupId>
      <artifactId>jersey2-api</artifactId>
    </dependency>
    <dependency>
      <groupId>io.jenkins.plugins</groupId>
      <artifactId>joda-time-api</artifactId>
    </dependency>
    <dependency>
      <groupId>io.jenkins.plugins</groupId>
      <artifactId>json-api</artifactId>
    </dependency>
    <!-- required for VersionComparator -->
    <dependency>
      <groupId>org.apache.maven</groupId>
      <artifactId>maven-artifact</artifactId>
      <version>3.9.14</version>
      <exclusions>
        <!-- Provided by commons-lang3-api plugin -->
        <exclusion>
          <groupId>org.apache.commons</groupId>
          <artifactId>commons-lang3</artifactId>
        </exclusion>
      </exclusions>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins</groupId>
      <artifactId>apache-httpcomponents-client-4-api</artifactId>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins</groupId>
      <artifactId>branch-api</artifactId>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins</groupId>
      <artifactId>credentials</artifactId>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins</groupId>
      <artifactId>jackson2-api</artifactId>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins</groupId>
      <artifactId>mailer</artifactId>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins</groupId>
      <artifactId>matrix-project</artifactId>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins</groupId>
      <artifactId>p4</artifactId>
      <version>1.17.1</version>
      <optional>true</optional>
      <exclusions>
        <exclusion>
          <groupId>org.apache.commons</groupId>
          <artifactId>commons-compress</artifactId>
        </exclusion>
        <exclusion>
          <groupId>org.jenkins-ci.plugins</groupId>
          <artifactId>*</artifactId>
        </exclusion>
      </exclusions>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins.workflow</groupId>
      <artifactId>workflow-job</artifactId>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins.workflow</groupId>
      <artifactId>workflow-step-api</artifactId>
      <optional>true</optional>
    </dependency>
    <dependency>
      <groupId>io.jenkins.configuration-as-code</groupId>
      <artifactId>test-harness</artifactId>
      <scope>test</scope>
    </dependency>
    <!-- test dependencies -->
    <!-- required to start p4 tests -->
    <dependency>
      <groupId>org.jenkins-ci.plugins</groupId>
      <artifactId>command-launcher</artifactId>
      <scope>test</scope>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins.workflow</groupId>
      <artifactId>workflow-basic-steps</artifactId>
      <scope>test</scope>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins.workflow</groupId>
      <artifactId>workflow-multibranch</artifactId>
      <scope>test</scope>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins.workflow</groupId>
      <artifactId>workflow-scm-step</artifactId>
      <scope>test</scope>
    </dependency>
    <dependency>
      <groupId>org.jenkins-ci.plugins.workflow</groupId>
      <artifactId>workflow-step-api</artifactId>
      <classifier>tests</classifier>
      <scope>test</scope>
    </dependency>
    <dependency>
      <groupId>org.mockito</groupId>
      <artifactId>mockito-core</artifactId>
      <scope>test</scope>
    </dependency>
    <dependency>
      <groupId>org.mockito</groupId>
      <artifactId>mockito-junit-jupiter</artifactId>
      <scope>test</scope>
    </dependency>
  </dependencies>

  <repositories>
    <repository>
      <releases>
        <enabled>true</enabled>
      </releases>
      <snapshots>
        <enabled>false</enabled>
      </snapshots>
      <id>repo.jenkins-ci.org</id>
      <url>https://repo.jenkins-ci.org/public/</url>
    </repository>
  </repositories>

  <pluginRepositories>
    <pluginRepository>
      <releases>
        <enabled>true</enabled>
      </releases>
      <snapshots>
        <enabled>false</enabled>
      </snapshots>
      <id>repo.jenkins-ci.org</id>
      <url>https://repo.jenkins-ci.org/public/</url>
    </pluginRepository>
  </pluginRepositories>

  <build>
    <plugins>
      <plugin>
        <groupId>org.eluder.coveralls</groupId>
        <artifactId>coveralls-maven-plugin</artifactId>
        <version>4.3.0</version>
        <!-- Explicit dependency on jaxb-api to avoid problems with
          JDK9 and later, until a new release is made:
          See also https://github.com/trautonen/coveralls-maven-plugin/issues/112
        -->
        <dependencies>
          <dependency>
            <groupId>javax.xml.bind</groupId>
            <artifactId>jaxb-api</artifactId>
            <version>2.3.1</version>
          </dependency>
        </dependencies>
      </plugin>
      <!-- spotbugs is defined in parent plugin-pom but overriding some things here -->
      <plugin>
        <groupId>com.github.spotbugs</groupId>
        <artifactId>spotbugs-maven-plugin</artifactId>
        <executions>
          <execution>
            <id>spotbugs</id>
            <goals>
              <goal>check</goal>
            </goals>
            <phase>verify</phase>
            <configuration>
              <failOnError>${spotbugs.failOnError}</failOnError>
              <effort>${spotbugs.effort}</effort>
              <threshold>${spotbugs.threshold}</threshold>
              <onlyAnalyze>hudson.plugins.jira.*</onlyAnalyze>
            </configuration>
          </execution>
        </executions>
      </plugin>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-surefire-plugin</artifactId>
        <configuration>
          <reuseForks>false</reuseForks>
          <!-- fix issues in test when trying to serialize some mocks and to run some tests within your IDE you will need this -->
          <systemPropertyVariables>
            <hudson.remoting.ClassFilter>hudson.plugins.jira.JiraFolderProperty,hudson.plugins.jira.JiraSite,hudson.plugins.jira.JiraJobAction,com.atlassian.jira.rest.client.api.domain.IssueType</hudson.remoting.ClassFilter>
          </systemPropertyVariables>
        </configuration>
      </plugin>
    </plugins>
  </build>
</project>


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/ApacheAsyncHttpClient.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import static io.atlassian.util.concurrent.Promises.rejected;
import static java.lang.String.format;

import com.atlassian.event.api.EventPublisher;
import com.atlassian.httpclient.api.DefaultResponseTransformation;
import com.atlassian.httpclient.api.HttpClient;
import com.atlassian.httpclient.api.HttpStatus;
import com.atlassian.httpclient.api.Request;
import com.atlassian.httpclient.api.Response;
import com.atlassian.httpclient.api.ResponsePromise;
import com.atlassian.httpclient.api.ResponsePromises;
import com.atlassian.httpclient.api.ResponseTransformation;
import com.atlassian.httpclient.api.factory.HttpClientOptions;
import com.atlassian.httpclient.base.event.HttpRequestCompletedEvent;
import com.atlassian.httpclient.base.event.HttpRequestFailedEvent;
import com.atlassian.sal.api.ApplicationProperties;
import com.atlassian.sal.api.executor.ThreadLocalContextManager;
import hudson.ProxyConfiguration;
import io.atlassian.util.concurrent.ThreadFactories;
import java.io.IOException;
import java.net.URI;
import java.security.GeneralSecurityException;
import java.security.KeyManagementException;
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
import java.security.cert.X509Certificate;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.TimeUnit;
import java.util.function.Function;
import java.util.function.Supplier;
import java.util.regex.Pattern;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLException;
import javax.net.ssl.SSLSession;
import javax.net.ssl.SSLSocket;
import jenkins.model.Jenkins;
import org.apache.commons.lang3.StringUtils;
import org.apache.http.Header;
import org.apache.http.HttpEntity;
import org.apache.http.HttpException;
import org.apache.http.HttpHost;
import org.apache.http.HttpRequest;
import org.apache.http.HttpResponse;
import org.apache.http.StatusLine;
import org.apache.http.auth.AuthScope;
import org.apache.http.auth.UsernamePasswordCredentials;
import org.apache.http.client.CredentialsProvider;
import org.apache.http.client.config.CookieSpecs;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.HttpDelete;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpHead;
import org.apache.http.client.methods.HttpOptions;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.client.methods.HttpPut;
import org.apache.http.client.methods.HttpRequestBase;
import org.apache.http.client.methods.HttpTrace;
import org.apache.http.config.Registry;
import org.apache.http.config.RegistryBuilder;
import org.apache.http.conn.ssl.SSLContextBuilder;
import org.apache.http.conn.ssl.TrustSelfSignedStrategy;
import org.apache.http.conn.ssl.X509HostnameVerifier;
import org.apache.http.impl.client.BasicCredentialsProvider;
import org.apache.http.impl.client.ProxyAuthenticationStrategy;
import org.apache.http.impl.conn.DefaultRoutePlanner;
import org.apache.http.impl.conn.DefaultSchemePortResolver;
import org.apache.http.impl.conn.SystemDefaultDnsResolver;
import org.apache.http.impl.nio.client.CloseableHttpAsyncClient;
import org.apache.http.impl.nio.client.HttpAsyncClientBuilder;
import org.apache.http.impl.nio.client.HttpAsyncClients;
import org.apache.http.impl.nio.conn.ManagedNHttpClientConnectionFactory;
import org.apache.http.impl.nio.conn.PoolingNHttpClientConnectionManager;
import org.apache.http.impl.nio.reactor.DefaultConnectingIOReactor;
import org.apache.http.impl.nio.reactor.IOReactorConfig;
import org.apache.http.nio.conn.NoopIOSessionStrategy;
import org.apache.http.nio.conn.SchemeIOSessionStrategy;
import org.apache.http.nio.conn.ssl.SSLIOSessionStrategy;
import org.apache.http.nio.reactor.IOReactorException;
import org.apache.http.nio.reactor.IOReactorExceptionHandler;
import org.apache.http.protocol.BasicHttpContext;
import org.apache.http.protocol.HttpContext;
import org.apache.http.util.Args;
import org.apache.http.util.TextUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.DisposableBean;

public final class ApacheAsyncHttpClient<C> implements HttpClient, DisposableBean {
    private final Logger log = LoggerFactory.getLogger(this.getClass());

    private static final Supplier<String> httpClientVersion =
            () -> MavenUtils.getVersion("com.atlassian.httpclient", "atlassian-httpclient-api");

    private final Function<Object, Void> eventConsumer;
    private final Supplier<String> applicationName;
    private final ThreadLocalContextManager<C> threadLocalContextManager;
    private final ExecutorService callbackExecutor;
    private final HttpClientOptions httpClientOptions;

    private final CloseableHttpAsyncClient nonCachingHttpClient;

    public ApacheAsyncHttpClient(
            EventPublisher eventConsumer,
            ApplicationProperties applicationProperties,
            ThreadLocalContextManager<C> threadLocalContextManager) {
        this(eventConsumer, applicationProperties, threadLocalContextManager, new HttpClientOptions());
    }

    public ApacheAsyncHttpClient(
            EventPublisher eventConsumer,
            ApplicationProperties applicationProperties,
            ThreadLocalContextManager<C> threadLocalContextManager,
            HttpClientOptions options) {
        this(
                new DefaultApplicationNameSupplier(applicationProperties),
                new EventConsumerFunction(eventConsumer),
                threadLocalContextManager,
                options);
    }

    public ApacheAsyncHttpClient(
            final Supplier<String> applicationName,
            final Function<Object, Void> eventConsumer,
            final ThreadLocalContextManager<C> threadLocalContextManager,
            final HttpClientOptions options) {
        this.eventConsumer = Objects.requireNonNull(eventConsumer);
        this.applicationName = Objects.requireNonNull(applicationName);
        this.threadLocalContextManager = Objects.requireNonNull(threadLocalContextManager);
        this.httpClientOptions = Objects.requireNonNull(options);

        try {
            final HttpAsyncClientBuilder clientBuilder = createClientBuilder();

            this.nonCachingHttpClient = clientBuilder.build();
            this.callbackExecutor = options.getCallbackExecutor();
            nonCachingHttpClient.start();
        } catch (IOReactorException e) {
            throw new RuntimeException("Reactor " + options.getThreadPrefix() + "not set up correctly", e);
        }
    }

    private HttpAsyncClientBuilder createClientBuilder() throws IOReactorException {

        final HttpClientOptions options = httpClientOptions;
        final IOReactorConfig reactorConfig = IOReactorConfig.custom()
                .setIoThreadCount(options.getIoThreadCount())
                .setSelectInterval(options.getIoSelectInterval())
                .setInterestOpQueued(true)
                .build();

        final DefaultConnectingIOReactor ioReactor = new DefaultConnectingIOReactor(reactorConfig);
        ioReactor.setExceptionHandler(new IOReactorExceptionHandler() {
            @Override
            public boolean handle(final IOException e) {
                log.error("IO exception in reactor ", e);
                return false;
            }

            @Override
            public boolean handle(final RuntimeException e) {
                log.error("Fatal runtime error", e);
                return false;
            }
        });

        final PoolingNHttpClientConnectionManager connectionManager =
                new PoolingNHttpClientConnectionManager(
                        ioReactor,
                        ManagedNHttpClientConnectionFactory.INSTANCE,
                        getRegistry(options),
                        DefaultSchemePortResolver.INSTANCE,
                        SystemDefaultDnsResolver.INSTANCE,
                        options.getConnectionPoolTimeToLive(),
                        TimeUnit.MILLISECONDS) {
                    @Override
                    protected void finalize() throws Throwable {
                        // prevent the PoolingClientAsyncConnectionManager from logging - this causes exceptions due to
                        // the ClassLoader probably having been removed when the plugin shuts down.  Added a
                        // PluginEventListener to make sure the shutdown method is called while the plugin classloader
                        // is still active.
                        try {
                            this.shutdown();
                        } catch (Throwable e) {
                            // ignore e.printStackTrace();
                        }
                    }
                };

        connectionManager.setDefaultMaxPerRoute(options.getMaxConnectionsPerHost());

        final RequestConfig requestConfig = RequestConfig.custom()
                .setConnectTimeout((int) options.getConnectionTimeout())
                .setConnectionRequestTimeout((int) options.getLeaseTimeout())
                .setCookieSpec(options.getIgnoreCookies() ? CookieSpecs.IGNORE_COOKIES : CookieSpecs.DEFAULT)
                .setSocketTimeout((int) options.getSocketTimeout())
                .build();

        final HttpAsyncClientBuilder clientBuilder = HttpAsyncClients.custom()
                .setThreadFactory(ThreadFactories.namedThreadFactory(
                        options.getThreadPrefix() + "-io", ThreadFactories.Type.DAEMON))
                .setDefaultIOReactorConfig(reactorConfig)
                .setConnectionManager(connectionManager)
                .setRedirectStrategy(new RedirectStrategy())
                .setUserAgent(getUserAgent(options))
                .setDefaultRequestConfig(requestConfig);

        if (Jenkins.get() != null) {
            ProxyConfiguration proxyConfiguration = Jenkins.getInstance().proxy;
            if (proxyConfiguration != null) {
                final HttpHost proxy = new HttpHost(proxyConfiguration.name, proxyConfiguration.port);
                // clientBuilder.setProxy( proxy );
                if (StringUtils.isNotBlank(proxyConfiguration.getUserName())) {
                    clientBuilder.setProxyAuthenticationStrategy(ProxyAuthenticationStrategy.INSTANCE);
                    CredentialsProvider credsProvider = new BasicCredentialsProvider();
                    credsProvider.setCredentials(
                            new AuthScope(proxyConfiguration.name, proxyConfiguration.port),
                            new UsernamePasswordCredentials(
                                    proxyConfiguration.getUserName(), proxyConfiguration.getPassword()));
                    clientBuilder.setDefaultCredentialsProvider(credsProvider);
                }

                clientBuilder.setRoutePlanner(
                        new JenkinsProxyRoutePlanner(proxy, proxyConfiguration.getNoProxyHostPatterns()));
            }
        }

        return clientBuilder;
    }

    private class JenkinsProxyRoutePlanner extends DefaultRoutePlanner {
        private final HttpHost proxy;
        private final List<Pattern> nonProxyHosts;

        public JenkinsProxyRoutePlanner(HttpHost proxy, List<Pattern> nonProxyHosts) {
            super(null);
            this.proxy = Args.notNull(proxy, "Proxy host");
            this.nonProxyHosts = nonProxyHosts;
        }

        @Override
        protected HttpHost determineProxy(HttpHost target, HttpRequest request, HttpContext context)
                throws HttpException {
            return bypassProxy(target.getHostName()) ? null : this.proxy;
        }

        private boolean bypassProxy(String host) {
            for (Pattern p : nonProxyHosts) {
                if (p.matcher(host).matches()) {
                    return true;
                }
            }
            return false;
        }
    }

    private Registry<SchemeIOSessionStrategy> getRegistry(final HttpClientOptions options) {
        try {
            final TrustSelfSignedStrategy strategy =
                    options.trustSelfSignedCertificates() ? new TrustSelfSignedStrategy() : null;

            final SSLContext sslContext = new SSLContextBuilder()
                    .useTLS()
                    .loadTrustMaterial(null, strategy)
                    .build();

            final SSLIOSessionStrategy sslioSessionStrategy = new SSLIOSessionStrategy(
                    sslContext,
                    split(System.getProperty("https.protocols")),
                    split(System.getProperty("https.cipherSuites")),
                    options.trustSelfSignedCertificates()
                            ? getSelfSignedVerifier()
                            : SSLIOSessionStrategy.BROWSER_COMPATIBLE_HOSTNAME_VERIFIER);

            return RegistryBuilder.<SchemeIOSessionStrategy>create()
                    .register("http", NoopIOSessionStrategy.INSTANCE)
                    .register("https", sslioSessionStrategy)
                    .build();
        } catch (KeyManagementException | NoSuchAlgorithmException | KeyStoreException e) {
            return getFallbackRegistry(e);
        }
    }

    private X509HostnameVerifier getSelfSignedVerifier() {
        return new X509HostnameVerifier() {
            @Override
            public void verify(final String host, final SSLSocket ssl) throws IOException {
                log.debug("Verification for certificates from {} disabled", host);
            }

            @Override
            public void verify(final String host, final X509Certificate cert) throws SSLException {
                log.debug("Verification for certificates from {} disabled", host);
            }

            @Override
            public void verify(final String host, final String[] cns, final String[] subjectAlts) throws SSLException {
                log.debug("Verification for certificates from {} disabled", host);
            }

            @Override
            public boolean verify(final String host, final SSLSession sslSession) {
                log.debug("Verification for certificates from {} disabled", host);
                return true;
            }
        };
    }

    private Registry<SchemeIOSessionStrategy> getFallbackRegistry(final GeneralSecurityException e) {
        log.error("Error when creating scheme session strategy registry", e);
        return RegistryBuilder.<SchemeIOSessionStrategy>create()
                .register("http", NoopIOSessionStrategy.INSTANCE)
                .register("https", SSLIOSessionStrategy.getDefaultStrategy())
                .build();
    }

    private String getUserAgent(HttpClientOptions options) {
        return format(
                "Atlassian HttpClient %s / %s / %s",
                httpClientVersion.get(), applicationName.get(), options.getUserAgent());
    }

    @Override
    public final ResponsePromise execute(final Request request) {
        try {
            return doExecute(request);
        } catch (Throwable t) {
            return ResponsePromises.toResponsePromise(rejected(t));
        }
    }

    private ResponsePromise doExecute(final Request request) {
        httpClientOptions.getRequestPreparer().accept(request);

        final long start = System.currentTimeMillis();
        final HttpRequestBase op;
        final String uri = request.getUri().toString();
        final Request.Method method = request.getMethod();
        switch (method) {
            case GET:
                op = new HttpGet(uri);
                break;
            case POST:
                op = new HttpPost(uri);
                break;
            case PUT:
                op = new HttpPut(uri);
                break;
            case DELETE:
                op = new HttpDelete(uri);
                break;
            case OPTIONS:
                op = new HttpOptions(uri);
                break;
            case HEAD:
                op = new HttpHead(uri);
                break;
            case TRACE:
                op = new HttpTrace(uri);
                break;
            default:
                throw new UnsupportedOperationException(method.toString());
        }
        if (request.hasEntity()) {
            new RequestEntityEffect(request).apply(op);
        }

        for (Map.Entry<String, String> entry : request.getHeaders().entrySet()) {
            op.setHeader(entry.getKey(), entry.getValue());
        }

        final PromiseHttpAsyncClient asyncClient = getPromiseHttpAsyncClient(request);
        return ResponsePromises.toResponsePromise(asyncClient
                .execute(op, new BasicHttpContext())
                .fold(
                        throwable -> {
                            final long requestDuration = System.currentTimeMillis() - start;
                            publishEvent(request, requestDuration, throwable);
                            throw new RuntimeException(throwable);
                        },
                        httpResponse -> {
                            final long requestDuration = System.currentTimeMillis() - start;
                            publishEvent(
                                    request,
                                    requestDuration,
                                    httpResponse.getStatusLine().getStatusCode());
                            try {
                                return translate(httpResponse);
                            } catch (IOException e) {
                                throw new RuntimeException(e);
                            }
                        }));
    }

    private void publishEvent(Request request, long requestDuration, int statusCode) {
        if (HttpStatus.OK.code <= statusCode && statusCode < HttpStatus.MULTIPLE_CHOICES.code) {
            eventConsumer.apply(new HttpRequestCompletedEvent(
                    request.getUri().toString(),
                    request.getMethod().name(),
                    statusCode,
                    requestDuration,
                    request.getAttributes()));
        } else {
            eventConsumer.apply(new HttpRequestFailedEvent(
                    request.getUri().toString(),
                    request.getMethod().name(),
                    statusCode,
                    requestDuration,
                    request.getAttributes()));
        }
    }

    private void publishEvent(Request request, long requestDuration, Throwable ex) {
        eventConsumer.apply(new HttpRequestFailedEvent(
                request.getUri().toString(),
                request.getMethod().name(),
                ex.toString(),
                requestDuration,
                request.getAttributes()));
    }

    private PromiseHttpAsyncClient getPromiseHttpAsyncClient(Request request) {

        log.trace("Creating new HttpAsyncClient");
        final CloseableHttpAsyncClient nonCachingHttpClient;
        try {
            final HttpAsyncClientBuilder clientBuilder = createClientBuilder();

            nonCachingHttpClient = clientBuilder.build();
            nonCachingHttpClient.start();
        } catch (IOReactorException e) {
            throw new RuntimeException("Reactor " + httpClientOptions.getThreadPrefix() + "not set up correctly", e);
        }

        return new CompletableFuturePromiseHttpPromiseAsyncClient<>(
                nonCachingHttpClient, threadLocalContextManager, callbackExecutor);
    }

    private Response translate(HttpResponse httpResponse) throws IOException {
        StatusLine status = httpResponse.getStatusLine();
        Response.Builder responseBuilder = DefaultResponse.builder()
                .setMaxEntitySize(httpClientOptions.getMaxEntitySize())
                .setStatusCode(status.getStatusCode())
                .setStatusText(status.getReasonPhrase());

        Header[] httpHeaders = httpResponse.getAllHeaders();
        for (Header httpHeader : httpHeaders) {
            responseBuilder.setHeader(httpHeader.getName(), httpHeader.getValue());
        }
        final HttpEntity entity = httpResponse.getEntity();
        if (entity != null) {
            responseBuilder.setEntityStream(entity.getContent());
        }
        return responseBuilder.build();
    }

    @Override
    public void destroy() throws Exception {
        try {
            callbackExecutor.shutdown();
        } catch (Exception e) {
            log.warn("skip fail to shutdown callbackExecutor:" + e.getMessage(), e);
        }
        try {
            nonCachingHttpClient.close();
        } catch (Exception e) {
            log.warn("skip fail to shutdown nonCachingHttpClient:" + e.getMessage(), e);
        }
    }

    @Override
    public void flushCacheByUriPattern(Pattern urlPattern) {
        // httpCacheStorage.flushByUriPattern(urlPattern);
    }

    private static final class NoOpThreadLocalContextManager<C> implements ThreadLocalContextManager<C> {
        @Override
        public C getThreadLocalContext() {
            return null;
        }

        @Override
        public void setThreadLocalContext(C context) {}

        @Override
        public void clearThreadLocalContext() {}
    }

    private static final class DefaultApplicationNameSupplier implements Supplier<String> {
        private final ApplicationProperties applicationProperties;

        public DefaultApplicationNameSupplier(ApplicationProperties applicationProperties) {
            this.applicationProperties = Objects.requireNonNull(applicationProperties);
        }

        @Override
        public String get() {
            return format(
                    "%s-%s (%s)",
                    applicationProperties.getDisplayName(),
                    applicationProperties.getVersion(),
                    applicationProperties.getBuildNumber());
        }
    }

    private static class EventConsumerFunction implements Function<Object, Void> {
        private final EventPublisher eventPublisher;

        public EventConsumerFunction(EventPublisher eventPublisher) {
            this.eventPublisher = eventPublisher;
        }

        @Override
        public Void apply(Object event) {
            if (eventPublisher != null) {
                eventPublisher.publish(event);
            }
            return null;
        }
    }

    private static String[] split(final String s) {
        if (TextUtils.isBlank(s)) {
            return null;
        }
        return s.split(" *, *");
    }

    @Override
    public Request.Builder newRequest() {
        return DefaultRequest.builder(this);
    }

    @Override
    public Request.Builder newRequest(URI uri) {
        return DefaultRequest.builder(this).setUri(uri);
    }

    @Override
    public Request.Builder newRequest(URI uri, String contentType, String entity) {
        return DefaultRequest.builder(this)
                .setContentType(contentType)
                .setEntity(entity)
                .setUri(uri);
    }

    @Override
    public Request.Builder newRequest(String uri) {
        return newRequest(URI.create(uri));
    }

    @Override
    public Request.Builder newRequest(String uri, String contentType, String entity) {
        return newRequest(URI.create(uri), contentType, entity);
    }

    @Override
    public <A> ResponseTransformation.Builder<A> transformation() {
        return DefaultResponseTransformation.builder();
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/CommonBuilder.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import com.atlassian.httpclient.api.Common;
import java.io.InputStream;
import java.nio.charset.Charset;
import java.util.Map;

public class CommonBuilder<T> implements Common<CommonBuilder<T>> {
    private final Headers.Builder headersBuilder = new Headers.Builder();
    private InputStream entityStream;

    @Override
    public CommonBuilder<T> setHeader(final String name, final String value) {
        headersBuilder.setHeader(name, value);
        return this;
    }

    @Override
    public CommonBuilder<T> setHeaders(final Map<String, String> headers) {
        headersBuilder.setHeaders(headers);
        return this;
    }

    @Override
    public CommonBuilder<T> setEntity(final String entity) {
        if (entity != null) {
            final String charset = "UTF-8";
            byte[] bytes = entity.getBytes(Charset.forName(charset));
            setEntityStream(new EntityByteArrayInputStream(bytes), charset);
        } else {
            setEntityStream(null, null);
        }
        return this;
    }

    @Override
    public CommonBuilder<T> setEntityStream(final InputStream entityStream) {
        this.entityStream = entityStream;
        return this;
    }

    @Override
    public CommonBuilder<T> setContentCharset(final String contentCharset) {
        headersBuilder.setContentCharset(contentCharset);
        return this;
    }

    @Override
    public CommonBuilder<T> setContentType(final String contentType) {
        headersBuilder.setContentType(contentType);
        return this;
    }

    @Override
    public CommonBuilder<T> setEntityStream(final InputStream entityStream, final String charset) {
        setEntityStream(entityStream);
        headersBuilder.setContentCharset(charset);
        return this;
    }

    public InputStream getEntityStream() {
        return entityStream;
    }

    public Headers getHeaders() {
        return headersBuilder.build();
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/CompletableFuturePromiseHttpPromiseAsyncClient.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import com.atlassian.sal.api.executor.ThreadLocalContextManager;
import io.atlassian.util.concurrent.Promise;
import io.atlassian.util.concurrent.Promises;
import java.io.IOException;
import java.util.Objects;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.Executor;
import java.util.concurrent.Future;
import java.util.concurrent.TimeoutException;
import org.apache.http.HttpResponse;
import org.apache.http.client.methods.HttpUriRequest;
import org.apache.http.concurrent.FutureCallback;
import org.apache.http.impl.nio.client.CloseableHttpAsyncClient;
import org.apache.http.protocol.HttpContext;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

final class CompletableFuturePromiseHttpPromiseAsyncClient<C> implements PromiseHttpAsyncClient {
    private final Logger log = LoggerFactory.getLogger(this.getClass());

    private final CloseableHttpAsyncClient client;
    private final ThreadLocalContextManager<C> threadLocalContextManager;
    private final Executor executor;

    CompletableFuturePromiseHttpPromiseAsyncClient(
            CloseableHttpAsyncClient client,
            ThreadLocalContextManager<C> threadLocalContextManager,
            Executor executor) {
        this.client = Objects.requireNonNull(client);
        this.threadLocalContextManager = Objects.requireNonNull(threadLocalContextManager);
        this.executor = new ThreadLocalDelegateExecutor<>(threadLocalContextManager, executor);
    }

    @Override
    public Promise<HttpResponse> execute(HttpUriRequest request, HttpContext context) {
        // TODO after migrating from atlassian-util-concurrent 3.0.0 to 4.0.0 the SettableFuture.create() maybe obsolete
        // ?
        CompletableFuture<HttpResponse> future = new CompletableFuture<>();
        Future<org.apache.http.HttpResponse> clientFuture = client.execute(
                request, context, new ThreadLocalContextAwareFutureCallback<C>(threadLocalContextManager) {

                    @Override
                    void doCompleted(final HttpResponse httpResponse) {
                        executor.execute(() -> future.complete(httpResponse));
                        log.trace("Closing in doCompleted()");
                        closeClient();
                    }

                    @Override
                    void doFailed(final Exception ex) {
                        executor.execute(() -> future.completeExceptionally(ex));
                        log.trace("Closing in doFailed()");
                        closeClient();
                    }

                    @Override
                    void doCancelled() {
                        final TimeoutException timeoutException = new TimeoutException();
                        executor.execute(() -> future.completeExceptionally(timeoutException));
                        log.trace("Closing in doCancelled()");
                        closeClient();
                    }
                });
        return Promises.forFuture(clientFuture, executor);
    }

    private void closeClient() {
        try {
            client.close();
        } catch (IOException e) {
            log.error("Close failed", e);
        }
    }

    static <C> void runInContext(
            ThreadLocalContextManager<C> threadLocalContextManager,
            C threadLocalContext,
            ClassLoader contextClassLoader,
            Runnable runnable) {
        final C oldThreadLocalContext = threadLocalContextManager.getThreadLocalContext();
        final ClassLoader oldCcl = Thread.currentThread().getContextClassLoader();
        try {
            Thread.currentThread().setContextClassLoader(contextClassLoader);
            threadLocalContextManager.setThreadLocalContext(threadLocalContext);
            runnable.run();
        } finally {
            threadLocalContextManager.setThreadLocalContext(oldThreadLocalContext);
            Thread.currentThread().setContextClassLoader(oldCcl);
        }
    }

    private abstract static class ThreadLocalContextAwareFutureCallback<C> implements FutureCallback<HttpResponse> {
        private final ThreadLocalContextManager<C> threadLocalContextManager;
        private final C threadLocalContext;
        private final ClassLoader contextClassLoader;

        private ThreadLocalContextAwareFutureCallback(ThreadLocalContextManager<C> threadLocalContextManager) {
            this.threadLocalContextManager = Objects.requireNonNull(threadLocalContextManager);
            this.threadLocalContext = threadLocalContextManager.getThreadLocalContext();
            this.contextClassLoader = Thread.currentThread().getContextClassLoader();
        }

        abstract void doCompleted(HttpResponse response);

        abstract void doFailed(Exception ex);

        abstract void doCancelled();

        @Override
        public final void completed(final HttpResponse response) {
            runInContext(
                    threadLocalContextManager, threadLocalContext, contextClassLoader, () -> doCompleted(response));
        }

        @Override
        public final void failed(final Exception ex) {
            runInContext(threadLocalContextManager, threadLocalContext, contextClassLoader, () -> doFailed(ex));
        }

        @Override
        public final void cancelled() {
            runInContext(threadLocalContextManager, threadLocalContext, contextClassLoader, this::doCancelled);
        }
    }

    private static final class ThreadLocalDelegateExecutor<C> implements Executor {
        private final Executor delegate;
        private final ThreadLocalContextManager<C> manager;

        ThreadLocalDelegateExecutor(ThreadLocalContextManager<C> manager, Executor delegate) {
            this.delegate = Objects.requireNonNull(delegate);
            this.manager = Objects.requireNonNull(manager);
        }

        @Override
        public void execute(Runnable runnable) {
            delegate.execute(new ThreadLocalDelegateRunnable<>(manager, runnable));
        }
    }

    private static final class ThreadLocalDelegateRunnable<C> implements Runnable {
        private final C context;
        private final Runnable delegate;
        private final ClassLoader contextClassLoader;
        private final ThreadLocalContextManager<C> manager;

        ThreadLocalDelegateRunnable(ThreadLocalContextManager<C> manager, Runnable delegate) {
            this.delegate = delegate;
            this.manager = manager;
            this.context = manager.getThreadLocalContext();
            this.contextClassLoader = Thread.currentThread().getContextClassLoader();
        }

        @Override
        public void run() {
            runInContext(manager, context, contextClassLoader, delegate);
        }
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/DefaultHttpClientFactory.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import com.atlassian.event.api.EventPublisher;
import com.atlassian.httpclient.api.HttpClient;
import com.atlassian.httpclient.api.factory.HttpClientFactory;
import com.atlassian.httpclient.api.factory.HttpClientOptions;
import com.atlassian.sal.api.ApplicationProperties;
import com.atlassian.sal.api.executor.ThreadLocalContextManager;
import edu.umd.cs.findbugs.annotations.NonNull;
import java.util.Objects;
import org.springframework.beans.factory.DisposableBean;

public final class DefaultHttpClientFactory implements HttpClientFactory, DisposableBean {
    private final EventPublisher eventPublisher;
    private final ApplicationProperties applicationProperties;
    private final ThreadLocalContextManager threadLocalContextManager;
    // shared http client
    private static ApacheAsyncHttpClient httpClient;

    public DefaultHttpClientFactory(
            EventPublisher eventPublisher,
            ApplicationProperties applicationProperties,
            ThreadLocalContextManager threadLocalContextManager) {
        this.eventPublisher = Objects.requireNonNull(eventPublisher);
        this.applicationProperties = Objects.requireNonNull(applicationProperties);
        this.threadLocalContextManager = Objects.requireNonNull(threadLocalContextManager);
    }

    @Override
    public HttpClient create(HttpClientOptions options) {
        return doCreate(options, threadLocalContextManager);
    }

    @Override
    public HttpClient create(HttpClientOptions options, ThreadLocalContextManager threadLocalContextManager) {
        return doCreate(options, threadLocalContextManager);
    }

    @Override
    public void dispose(@NonNull final HttpClient httpClient) throws Exception {
        if (httpClient instanceof ApacheAsyncHttpClient) {
            ((ApacheAsyncHttpClient) httpClient).destroy();
        }
    }

    private HttpClient doCreate(HttpClientOptions options, ThreadLocalContextManager threadLocalContextManager) {
        Objects.requireNonNull(options);
        // we create only one http client instance as we don't need more

        if (httpClient != null) {
            return httpClient;
        }
        synchronized (this) {
            httpClient = new ApacheAsyncHttpClient(
                    eventPublisher, applicationProperties, threadLocalContextManager, options);
            return httpClient;
        }
    }

    @Override
    public void destroy() throws Exception {
        httpClient.destroy();
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/DefaultMessage.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import com.atlassian.httpclient.api.Message;
import io.atlassian.fugue.Option;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.Reader;
import java.nio.charset.Charset;
import java.util.Map;
import org.apache.http.util.CharArrayBuffer;

/**
 * An abstract base class for HTTP messages (i.e. Request and Response) with support for
 * header and entity management.
 */
abstract class DefaultMessage implements Message {
    private final InputStream entityStream;
    private final Headers headers;
    private final long maxEntitySize;
    private boolean hasRead;

    public DefaultMessage(final Headers headers, final InputStream entityStream, Option<Long> maxEntitySize) {
        this.maxEntitySize = maxEntitySize.getOrElse((long) Integer.MAX_VALUE);
        this.headers = headers;
        this.entityStream = entityStream;
    }

    @Override
    public String getContentType() {
        return headers.getContentType();
    }

    @Override
    public String getContentCharset() {
        return headers.getContentCharset();
    }

    public String getAccept() {
        return headers.getHeader("Accept");
    }

    @Override
    public InputStream getEntityStream() throws IllegalStateException {
        checkRead();
        return entityStream;
    }

    @Override
    public String getEntity() throws IllegalStateException, IllegalArgumentException {
        String entity = null;
        if (hasEntity()) {
            checkValidSize();
            final String charsetAsString = getContentCharset();
            final Charset charset =
                    charsetAsString != null ? Charset.forName(charsetAsString) : Charset.forName("UTF-8");
            try {
                InputStream instream = getEntityStream();
                if (instream == null) {
                    return null;
                }
                try {
                    int bufferLength = 4096;
                    String lengthHeader = getHeader("Content-Length");
                    if (lengthHeader != null) {
                        bufferLength = Integer.parseInt(lengthHeader);
                    }

                    Reader reader = new InputStreamReader(instream, charset);
                    CharArrayBuffer buffer = new CharArrayBuffer(bufferLength);
                    char[] tmp = new char[1024];
                    int l;
                    while ((l = reader.read(tmp)) != -1) {
                        if (buffer.length() + l > maxEntitySize) {
                            throw new IllegalArgumentException("HTTP entity too large to be buffered in memory");
                        }
                        buffer.append(tmp, 0, l);
                    }
                    return buffer.toString();
                } finally {
                    instream.close();
                }
            } catch (IOException e) {
                throw new IllegalStateException("Unable to convert response body to String", e);
            }
        }
        return entity;
    }

    @Override
    public boolean hasEntity() {
        return entityStream != null;
    }

    @Override
    public boolean hasReadEntity() {
        return hasRead;
    }

    @Override
    public Map<String, String> getHeaders() {
        return headers.getHeaders();
    }

    @Override
    public String getHeader(String name) {
        return headers.getHeader(name);
    }

    public Message validate() {
        if (hasEntity() && headers.getContentType() == null) {
            throw new IllegalStateException("Property contentType must be set when entity is present");
        }
        return this;
    }

    private void checkRead() throws IllegalStateException {
        if (entityStream != null) {
            if (hasRead) {
                throw new IllegalStateException("Entity may only be accessed once");
            }
            hasRead = true;
        }
    }

    private void checkValidSize() throws IllegalArgumentException {
        Integer contentLength;
        String lengthHeader = getHeader("Content-Length");
        if (lengthHeader != null) {
            contentLength = Integer.parseInt(lengthHeader);
            if (contentLength > maxEntitySize) {
                throw new IllegalArgumentException("HTTP entity too large to be buffered in memory");
            }
        }
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/DefaultRequest.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import static com.atlassian.httpclient.api.Request.Method.DELETE;
import static com.atlassian.httpclient.api.Request.Method.GET;
import static com.atlassian.httpclient.api.Request.Method.HEAD;
import static com.atlassian.httpclient.api.Request.Method.OPTIONS;
import static com.atlassian.httpclient.api.Request.Method.POST;
import static com.atlassian.httpclient.api.Request.Method.PUT;
import static com.atlassian.httpclient.api.Request.Method.TRACE;

import com.atlassian.httpclient.api.EntityBuilder;
import com.atlassian.httpclient.api.HttpClient;
import com.atlassian.httpclient.api.Request;
import com.atlassian.httpclient.api.ResponsePromise;
import io.atlassian.fugue.Option;
import java.io.InputStream;
import java.net.URI;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import java.util.Objects;

public class DefaultRequest extends DefaultMessage implements Request {
    private final URI uri;
    private final boolean cacheDisabled;
    private final Map<String, String> attributes;
    private final Method method;
    private final Option<Long> contentLength;

    private DefaultRequest(
            URI uri,
            boolean cacheDisabled,
            Map<String, String> attributes,
            Headers headers,
            Method method,
            InputStream entityStream,
            Option<Long> contentLength) {
        super(headers, entityStream, Option.none());
        this.uri = uri;
        this.cacheDisabled = cacheDisabled;
        this.attributes = attributes;
        this.method = method;
        this.contentLength = contentLength;
    }

    public static DefaultRequestBuilder builder(HttpClient httpClient) {
        return new DefaultRequestBuilder(httpClient);
    }

    @Override
    public Method getMethod() {
        return method;
    }

    @Override
    public URI getUri() {
        return uri;
    }

    @Override
    public String getAccept() {
        return super.getAccept();
    }

    @Override
    public String getAttribute(String name) {
        return attributes.get(name);
    }

    @Override
    public Map<String, String> getAttributes() {
        return Collections.unmodifiableMap(attributes);
    }

    @Override
    public Option<Long> getContentLength() {
        return contentLength;
    }

    @Override
    public boolean isCacheDisabled() {
        return cacheDisabled;
    }

    @Override
    public Request validate() {
        super.validate();

        Objects.nonNull(uri);
        Objects.nonNull(method);

        switch (method) {
            case GET:
            case DELETE:
            case HEAD:
                if (hasEntity()) {
                    throw new IllegalStateException("Request method " + method + " does not support an entity");
                }
                break;
            case POST:
            case PUT:
            case TRACE:
                // no-op
                break;
        }
        return this;
    }

    public static class DefaultRequestBuilder implements Request.Builder {
        private final HttpClient httpClient;
        private final Map<String, String> attributes;
        private final CommonBuilder<DefaultRequest> commonBuilder;

        private URI uri;
        private boolean cacheDisabled;
        private Method method;
        private Option<Long> contentLength;

        public DefaultRequestBuilder(final HttpClient httpClient) {
            this.httpClient = httpClient;
            this.attributes = new HashMap<>();
            commonBuilder = new CommonBuilder<>();
            setAccept("*/*");
            contentLength = Option.none();
        }

        @Override
        public DefaultRequestBuilder setUri(final URI uri) {
            this.uri = uri;
            return this;
        }

        @Override
        public DefaultRequestBuilder setAccept(final String accept) {
            setHeader("Accept", accept);
            return this;
        }

        @Override
        public DefaultRequestBuilder setCacheDisabled() {
            this.cacheDisabled = true;
            return this;
        }

        @Override
        public DefaultRequestBuilder setAttribute(final String name, final String value) {
            attributes.put(name, value);
            return this;
        }

        @Override
        public DefaultRequestBuilder setAttributes(final Map<String, String> properties) {
            attributes.putAll(properties);
            return this;
        }

        @Override
        public DefaultRequestBuilder setEntity(final EntityBuilder entityBuilder) {
            EntityBuilder.Entity entity = entityBuilder.build();
            final Map<String, String> headers = entity.getHeaders();
            for (Map.Entry<String, String> headerEntry : headers.entrySet()) {
                setHeader(headerEntry.getKey(), headerEntry.getValue());
            }
            setEntityStream(entity.getInputStream());
            return this;
        }

        @Override
        public DefaultRequestBuilder setHeader(final String name, final String value) {
            commonBuilder.setHeader(name, value);
            return this;
        }

        @Override
        public DefaultRequestBuilder setHeaders(final Map<String, String> headers) {
            commonBuilder.setHeaders(headers);
            return this;
        }

        @Override
        public DefaultRequestBuilder setEntity(final String entity) {
            commonBuilder.setEntity(entity);
            setContentLength(entity.length());
            return this;
        }

        @Override
        public DefaultRequestBuilder setEntityStream(final InputStream entityStream) {
            commonBuilder.setEntityStream(entityStream);
            return this;
        }

        @Override
        public DefaultRequestBuilder setContentCharset(final String contentCharset) {
            commonBuilder.setContentCharset(contentCharset);
            return this;
        }

        @Override
        public DefaultRequestBuilder setContentType(final String contentType) {
            commonBuilder.setContentType(contentType);
            return this;
        }

        @Override
        public DefaultRequestBuilder setEntityStream(final InputStream entityStream, final String charset) {
            setEntityStream(entityStream);
            commonBuilder.setContentCharset(charset);
            return this;
        }

        @Override
        public DefaultRequestBuilder setContentLength(final long contentLength) {
            if (contentLength < 0) {
                throw new IllegalArgumentException("Content length must be greater than or equal to 0");
            }
            this.contentLength = Option.some(contentLength);
            return this;
        }

        @Override
        public DefaultRequest build() {
            return new DefaultRequest(
                    uri,
                    cacheDisabled,
                    attributes,
                    commonBuilder.getHeaders(),
                    method,
                    commonBuilder.getEntityStream(),
                    contentLength);
        }

        @Override
        public ResponsePromise get() {
            return execute(GET);
        }

        @Override
        public ResponsePromise post() {
            return execute(POST);
        }

        @Override
        public ResponsePromise put() {
            return execute(PUT);
        }

        @Override
        public ResponsePromise delete() {
            return execute(DELETE);
        }

        @Override
        public ResponsePromise options() {
            return execute(OPTIONS);
        }

        @Override
        public ResponsePromise head() {
            return execute(HEAD);
        }

        @Override
        public ResponsePromise trace() {
            return execute(TRACE);
        }

        @Override
        public ResponsePromise execute(Method method) {
            Objects.nonNull(method);
            setMethod(method);
            return httpClient.execute(build().validate());
        }

        public void setMethod(final Method method) {
            this.method = method;
        }
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/DefaultResponse.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import com.atlassian.httpclient.api.Response;
import io.atlassian.fugue.Option;
import java.io.InputStream;
import java.util.Map;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public final class DefaultResponse extends DefaultMessage implements Response {
    private int statusCode;
    private String statusText;
    private Logger log = LoggerFactory.getLogger(DefaultResponse.class);

    public DefaultResponse(
            Headers headers, InputStream entityStream, Option<Long> maxEntitySize, int statusCode, String statusText) {
        super(headers, entityStream, maxEntitySize);
        this.statusCode = statusCode;
        this.statusText = statusText;
    }

    public static DefaultResponseBuilder builder() {
        return new DefaultResponseBuilder();
    }

    @Override
    public int getStatusCode() {
        return statusCode;
    }

    @Override
    public String getStatusText() {
        return statusText;
    }

    @Override
    public boolean isInformational() {
        return statusCode >= 100 && statusCode < 200;
    }

    @Override
    public boolean isSuccessful() {
        return statusCode >= 200 && statusCode < 300;
    }

    @Override
    public boolean isOk() {
        return statusCode == 200;
    }

    @Override
    public boolean isCreated() {
        return statusCode == 201;
    }

    @Override
    public boolean isNoContent() {
        return statusCode == 204;
    }

    @Override
    public boolean isRedirection() {
        return statusCode >= 300 && statusCode < 400;
    }

    @Override
    public boolean isSeeOther() {
        return statusCode == 303;
    }

    @Override
    public boolean isNotModified() {
        return statusCode == 304;
    }

    @Override
    public boolean isClientError() {
        return statusCode >= 400 && statusCode < 500;
    }

    @Override
    public boolean isBadRequest() {
        return statusCode == 400;
    }

    @Override
    public boolean isUnauthorized() {
        return statusCode == 401;
    }

    @Override
    public boolean isForbidden() {
        return statusCode == 403;
    }

    @Override
    public boolean isNotFound() {
        return statusCode == 404;
    }

    @Override
    public boolean isConflict() {
        return statusCode == 409;
    }

    @Override
    public boolean isServerError() {
        return statusCode >= 500 && statusCode < 600;
    }

    @Override
    public boolean isInternalServerError() {
        return statusCode == 500;
    }

    @Override
    public boolean isServiceUnavailable() {
        return statusCode == 503;
    }

    @Override
    public boolean isError() {
        return isClientError() || isServerError();
    }

    @Override
    public boolean isNotSuccessful() {
        return isInformational() || isRedirection() || isError();
    }

    @Override
    public Option<Long> getContentLength() {
        String lengthString = getHeader(Headers.Names.CONTENT_LENGTH);
        if (lengthString != null) {
            try {
                Option<Long> parsedLength = Option.some(Long.parseLong(lengthString));
                return parsedLength.flatMap(aLong -> {
                    if (aLong < 0) {
                        log.warn("Unable to parse content length. Received out of range value {}", aLong);
                        return Option.none();
                    } else {
                        return Option.some(aLong);
                    }
                });
            } catch (NumberFormatException e) {
                log.warn("Unable to parse content length {}", lengthString);
                return Option.none();
            }
        } else {
            return Option.none();
        }
    }

    public static class DefaultResponseBuilder implements Builder {
        private final CommonBuilder<DefaultResponse> commonBuilder;

        private String statusText;
        private int statusCode;
        private long maxEntitySize;

        private DefaultResponseBuilder() {
            this.commonBuilder = new CommonBuilder<DefaultResponse>();
        }

        @Override
        public DefaultResponseBuilder setContentType(final String contentType) {
            commonBuilder.setContentType(contentType);
            return this;
        }

        @Override
        public DefaultResponseBuilder setContentCharset(final String contentCharset) {
            commonBuilder.setContentCharset(contentCharset);
            return this;
        }

        @Override
        public DefaultResponseBuilder setHeaders(final Map<String, String> headers) {
            commonBuilder.setHeaders(headers);
            return this;
        }

        @Override
        public DefaultResponseBuilder setHeader(final String name, final String value) {
            commonBuilder.setHeader(name, value);
            return this;
        }

        @Override
        public DefaultResponseBuilder setEntity(final String entity) {
            commonBuilder.setEntity(entity);
            return this;
        }

        @Override
        public DefaultResponseBuilder setEntityStream(final InputStream entityStream, final String encoding) {
            commonBuilder.setEntityStream(entityStream);
            commonBuilder.setContentCharset(encoding);
            return this;
        }

        @Override
        public DefaultResponseBuilder setEntityStream(final InputStream entityStream) {
            commonBuilder.setEntityStream(entityStream);
            return this;
        }

        @Override
        public DefaultResponseBuilder setStatusText(final String statusText) {
            this.statusText = statusText;
            return this;
        }

        @Override
        public DefaultResponseBuilder setStatusCode(final int statusCode) {
            this.statusCode = statusCode;
            return this;
        }

        public DefaultResponseBuilder setMaxEntitySize(long maxEntitySize) {
            this.maxEntitySize = maxEntitySize;
            return this;
        }

        @Override
        public DefaultResponse build() {
            return new DefaultResponse(
                    commonBuilder.getHeaders(),
                    commonBuilder.getEntityStream(),
                    Option.option(maxEntitySize),
                    statusCode,
                    statusText);
        }
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/EntityByteArrayInputStream.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import java.io.ByteArrayInputStream;

public class EntityByteArrayInputStream extends ByteArrayInputStream {
    private byte[] bytes;

    public EntityByteArrayInputStream(byte[] bytes) {
        super(bytes);
        this.bytes = bytes;
    }

    public byte[] getBytes() {
        return bytes;
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/Headers.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import com.atlassian.httpclient.api.Buildable;
import java.nio.charset.Charset;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import org.apache.http.protocol.HTTP;

public class Headers {
    private final Map<String, String> headers;
    private final String contentCharset;
    private final String contentType;

    private Headers(Map<String, String> headers, String contentCharset, String contentType) {
        this.headers = headers;
        this.contentCharset = contentCharset;
        this.contentType = contentType;
    }

    public String getContentCharset() {
        return contentCharset;
    }

    public String getContentType() {
        return contentType;
    }

    public Map<String, String> getHeaders() {
        Map<String, String> headers = new HashMap<>(this.headers);
        if (contentType != null) {
            headers.put(Names.CONTENT_TYPE, buildContentType());
        }
        return Collections.unmodifiableMap(headers);
    }

    public String getHeader(final String name) {
        String value;
        if (name.equalsIgnoreCase(Names.CONTENT_TYPE)) {
            value = buildContentType();
        } else {
            value = headers.get(name);
        }
        return value;
    }

    private String buildContentType() {
        String value = contentType != null ? contentType : "text/plain";
        if (contentCharset != null) {
            value += "; charset=" + contentCharset;
        }
        return value;
    }

    public static class Builder implements Buildable<Headers> {
        private final Map<String, String> headers = new HashMap<>();
        private String contentType;
        private String contentCharset;

        public Builder setHeaders(Map<String, String> headers) {
            this.headers.clear();
            for (Map.Entry<String, String> entry : headers.entrySet()) {
                setHeader(entry.getKey(), entry.getValue());
            }
            return this;
        }

        public Builder setHeader(String name, String value) {
            if (name.equalsIgnoreCase("Content-Type")) {
                parseContentType(value);
            } else {
                headers.put(name, value);
            }
            return this;
        }

        public Builder setContentLength(long contentLength) {
            if (contentLength < 0) {
                throw new IllegalArgumentException("Content-Length must be greater than or equal to 0");
            }
            setHeader(Names.CONTENT_LENGTH, Long.toString(contentLength));
            return this;
        }

        public Builder setContentCharset(String contentCharset) {
            this.contentCharset =
                    contentCharset != null ? Charset.forName(contentCharset).name() : null;
            return this;
        }

        public Builder setContentType(String contentType) {
            parseContentType(contentType);
            return this;
        }

        private void parseContentType(String value) {
            if (value != null) {
                String[] parts = value.split(";");
                if (parts.length >= 1) {
                    contentType = parts[0].trim();
                }
                if (parts.length >= 2) {
                    String subtype = parts[1].trim();
                    if (subtype.startsWith("charset=")) {
                        setContentCharset(subtype.substring(8));
                    } else if (subtype.startsWith("boundary=")) {
                        contentType = contentType.concat(';' + subtype);
                    }
                }
            } else {
                contentType = null;
            }
        }

        @Override
        public Headers build() {
            return new Headers(headers, contentCharset, contentType);
        }
    }

    public static class Names {
        public static final String CONTENT_LENGTH = HTTP.CONTENT_LEN;
        public static final String CONTENT_TYPE = HTTP.CONTENT_TYPE;

        private Names() {}
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/MavenUtils.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import static java.lang.String.format;

import java.io.InputStream;
import java.util.Properties;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

final class MavenUtils {
    private static final Logger logger = LoggerFactory.getLogger(MavenUtils.class);

    private static final String UNKNOWN_VERSION = "unknown";

    static String getVersion(String groupId, String artifactId) {
        final Properties props = new Properties();

        try (InputStream is = Thread.currentThread()
                .getContextClassLoader()
                .getResourceAsStream(getPomFilePath(groupId, artifactId))) {
            props.load(is);
            return props.getProperty("version", UNKNOWN_VERSION);
        } catch (Exception e) {
            logger.debug("Could not find version for maven artifact {}:{}", groupId, artifactId);
            logger.debug("Got the following exception:", e);
            return UNKNOWN_VERSION;
        }
    }

    private static String getPomFilePath(String groupId, String artifactId) {
        return format("META-INF/maven/%s/%s/pom.properties", groupId, artifactId);
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/PromiseHttpAsyncClient.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import io.atlassian.util.concurrent.Promise;
import org.apache.http.HttpResponse;
import org.apache.http.client.methods.HttpUriRequest;
import org.apache.http.protocol.HttpContext;

interface PromiseHttpAsyncClient {
    Promise<HttpResponse> execute(HttpUriRequest request, HttpContext context);
}


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/RedirectStrategy.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import java.net.URI;
import org.apache.http.HttpEntityEnclosingRequest;
import org.apache.http.HttpRequest;
import org.apache.http.HttpResponse;
import org.apache.http.ProtocolException;
import org.apache.http.client.methods.HttpDelete;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpHead;
import org.apache.http.client.methods.HttpPatch;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.client.methods.HttpPut;
import org.apache.http.client.methods.HttpUriRequest;
import org.apache.http.impl.client.DefaultRedirectStrategy;
import org.apache.http.protocol.HttpContext;

public class RedirectStrategy extends DefaultRedirectStrategy {
    final String[] REDIRECT_METHODS = {
        HttpHead.METHOD_NAME,
        HttpGet.METHOD_NAME,
        HttpPost.METHOD_NAME,
        HttpPut.METHOD_NAME,
        HttpDelete.METHOD_NAME,
        HttpPatch.METHOD_NAME
    };

    @Override
    public boolean isRedirectable(String method) {
        for (String m : REDIRECT_METHODS) {
            if (m.equalsIgnoreCase(method)) {
                return true;
            }
        }
        return false;
    }

    @Override
    public HttpUriRequest getRedirect(final HttpRequest request, final HttpResponse response, final HttpContext context)
            throws ProtocolException {
        URI uri = getLocationURI(request, response, context);
        String method = request.getRequestLine().getMethod();
        if (method.equalsIgnoreCase(HttpHead.METHOD_NAME)) {
            return new HttpHead(uri);
        } else if (method.equalsIgnoreCase(HttpGet.METHOD_NAME)) {
            return new HttpGet(uri);
        } else if (method.equalsIgnoreCase(HttpPost.METHOD_NAME)) {
            final HttpPost post = new HttpPost(uri);
            if (request instanceof HttpEntityEnclosingRequest) {
                post.setEntity(((HttpEntityEnclosingRequest) request).getEntity());
            }
            return post;
        } else if (method.equalsIgnoreCase(HttpPut.METHOD_NAME)) {
            return new HttpPut(uri);
        } else if (method.equalsIgnoreCase(HttpDelete.METHOD_NAME)) {
            return new HttpDelete(uri);
        } else if (method.equalsIgnoreCase(HttpPatch.METHOD_NAME)) {
            return new HttpPatch(uri);
        } else {
            return new HttpGet(uri);
        }
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/RequestEntityEffect.java
================================================
package com.atlassian.httpclient.apache.httpcomponents;

import com.atlassian.httpclient.api.Request;
import io.atlassian.fugue.Effect;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import org.apache.commons.io.IOUtils;
import org.apache.http.HttpEntity;
import org.apache.http.client.methods.HttpEntityEnclosingRequestBase;
import org.apache.http.client.methods.HttpRequestBase;
import org.apache.http.entity.ByteArrayEntity;
import org.apache.http.entity.InputStreamEntity;

public class RequestEntityEffect implements Effect<HttpRequestBase> {
    private final Request request;

    public RequestEntityEffect(final Request request) {
        this.request = request;
    }

    @Override
    public void apply(final HttpRequestBase httpRequestBase) {
        if (httpRequestBase instanceof HttpEntityEnclosingRequestBase) {
            ((HttpEntityEnclosingRequestBase) httpRequestBase).setEntity(getHttpEntity(request));
        } else {
            throw new UnsupportedOperationException(
                    "HTTP method " + request.getMethod() + " does not support sending an entity");
        }
    }

    private HttpEntity getHttpEntity(final Request request) {
        HttpEntity entity = null;
        if (request.hasEntity()) {
            InputStream entityStream = request.getEntityStream();
            if (entityStream instanceof ByteArrayInputStream) {
                byte[] bytes;
                if (entityStream instanceof EntityByteArrayInputStream) {
                    bytes = ((EntityByteArrayInputStream) entityStream).getBytes();
                } else {
                    try {
                        bytes = IOUtils.toByteArray(entityStream);
                    } catch (IOException e) {
                        throw new RuntimeException(e);
                    }
                }
                entity = new ByteArrayEntity(bytes);
            } else {
                long contentLength = request.getContentLength().getOrElse(-1L);
                entity = new InputStreamEntity(entityStream, contentLength);
            }
        }
        return entity;
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/base/event/AbstractHttpRequestEvent.java
================================================
package com.atlassian.httpclient.base.event;

import java.util.Map;

abstract class AbstractHttpRequestEvent {
    private final String url;
    private final String httpMethod;
    private final long requestDuration;
    private final Map<String, String> properties;

    private int statusCode;
    private String error;

    public AbstractHttpRequestEvent(
            String url, String httpMethod, int statusCode, long requestDuration, Map<String, String> properties) {
        this.url = url;
        this.httpMethod = httpMethod;
        this.statusCode = statusCode;
        this.requestDuration = requestDuration;
        this.properties = properties;
    }

    public AbstractHttpRequestEvent(
            String url, String httpMethod, String error, long requestDuration, Map<String, String> properties) {
        this.url = url;
        this.httpMethod = httpMethod;
        this.error = error;
        this.requestDuration = requestDuration;
        this.properties = properties;
    }

    public String getUrl() {
        return url;
    }

    public int getStatusCode() {
        return statusCode;
    }

    public String getError() {
        return error;
    }

    public long getRequestDuration() {
        return requestDuration;
    }

    public Map<String, String> getProperties() {
        return properties;
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/base/event/HttpRequestCompletedEvent.java
================================================
package com.atlassian.httpclient.base.event;

import java.util.Map;

public final class HttpRequestCompletedEvent extends AbstractHttpRequestEvent {
    public HttpRequestCompletedEvent(
            String url, String httpMethod, int statusCode, long requestDuration, Map<String, String> properties) {
        super(url, httpMethod, statusCode, requestDuration, properties);
    }
}


================================================
FILE: src/main/java/com/atlassian/httpclient/base/event/HttpRequestFailedEvent.java
================================================
package com.atlassian.httpclient.base.event;

import java.util.Map;

public final class HttpRequestFailedEvent extends AbstractHttpRequestEvent {
    public HttpRequestFailedEvent(
            String url, String httpMethod, int statusCode, long elapsed, Map<String, String> properties) {
        super(url, httpMethod, statusCode, elapsed, properties);
    }

    public HttpRequestFailedEvent(
            String url, String httpMethod, String error, long elapsed, Map<String, String> properties) {
        super(url, httpMethod, error, elapsed, properties);
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/CredentialsHelper.java
================================================
package hudson.plugins.jira;

import com.cloudbees.plugins.credentials.CredentialsMatchers;
import com.cloudbees.plugins.credentials.CredentialsProvider;
import com.cloudbees.plugins.credentials.CredentialsScope;
import com.cloudbees.plugins.credentials.SystemCredentialsProvider;
import com.cloudbees.plugins.credentials.common.StandardCredentials;
import com.cloudbees.plugins.credentials.common.StandardListBoxModel;
import com.cloudbees.plugins.credentials.common.StandardUsernamePasswordCredentials;
import com.cloudbees.plugins.credentials.common.UsernamePasswordCredentials;
import com.cloudbees.plugins.credentials.domains.URIRequirementBuilder;
import com.cloudbees.plugins.credentials.impl.UsernamePasswordCredentialsImpl;
import edu.umd.cs.findbugs.annotations.CheckForNull;
import edu.umd.cs.findbugs.annotations.NonNull;
import hudson.model.Descriptor.FormException;
import hudson.model.Item;
import hudson.model.Queue;
import hudson.model.queue.Tasks;
import hudson.security.ACL;
import hudson.util.FormValidation;
import hudson.util.ListBoxModel;
import hudson.util.Secret;
import java.io.IOException;
import java.net.URL;
import java.util.List;
import java.util.Optional;
import java.util.logging.Level;
import java.util.logging.Logger;
import jenkins.model.Jenkins;
import org.apache.commons.lang3.StringUtils;

/**
 * Helper class for vary credentials operations.
 *
 * @author Zhenlei Huang
 */
public class CredentialsHelper {
    private static final Logger LOGGER = Logger.getLogger(CredentialsHelper.class.getName());

    @CheckForNull
    protected static StandardUsernamePasswordCredentials lookupSystemCredentials(
            @CheckForNull String credentialsId, @CheckForNull URL url) {
        if (credentialsId == null) {
            return null;
        }
        return CredentialsMatchers.firstOrNull(
                CredentialsProvider.lookupCredentials(
                        StandardUsernamePasswordCredentials.class,
                        Jenkins.get(),
                        ACL.SYSTEM,
                        URIRequirementBuilder.fromUri(url != null ? url.toExternalForm() : null)
                                .build()),
                CredentialsMatchers.withId(credentialsId));
    }

    protected static StandardUsernamePasswordCredentials migrateCredentials(
            @NonNull String username, String password, @CheckForNull URL url) throws FormException {
        List<StandardUsernamePasswordCredentials> credentials = CredentialsMatchers.filter(
                CredentialsProvider.lookupCredentials(
                        StandardUsernamePasswordCredentials.class,
                        Jenkins.get(),
                        ACL.SYSTEM,
                        URIRequirementBuilder.fromUri(url != null ? url.toExternalForm() : null)
                                .build()),
                CredentialsMatchers.withUsername(username));
        for (StandardUsernamePasswordCredentials c : credentials) {
            if (StringUtils.equals(password, Secret.toString(c.getPassword()))) {
                return c; // found
            }
        }

        // Create new credentials with the principal and secret if we couldn't find any existing credentials
        StandardUsernamePasswordCredentials newCredentials = new UsernamePasswordCredentialsImpl(
                CredentialsScope.SYSTEM, null, "Migrated by Jira Plugin", username, password);
        SystemCredentialsProvider.getInstance().getCredentials().add(newCredentials);
        try {
            SystemCredentialsProvider.getInstance().save();
            LOGGER.log(
                    Level.INFO,
                    "Provided username and password were successfully migrated and stored as {0}",
                    newCredentials.getId());
        } catch (IOException e) {
            LOGGER.log(Level.WARNING, "Unable to store migrated credentials", e);
        }

        return newCredentials;
    }

    protected static ListBoxModel doFillCredentialsIdItems(Item item, String credentialsId, String uri) {
        StandardListBoxModel result = new StandardListBoxModel();
        if (item == null) {
            if (!Jenkins.get().hasPermission(Jenkins.ADMINISTER)) {
                return result.includeCurrentValue(credentialsId);
            }
        } else {
            if (!item.hasPermission(Item.EXTENDED_READ) && !item.hasPermission(CredentialsProvider.USE_ITEM)) {
                return result.includeCurrentValue(credentialsId);
            }
        }
        return result.includeEmptyValue()
                .includeMatchingAs(
                        item instanceof Queue.Task ? Tasks.getAuthenticationOf((Queue.Task) item) : ACL.SYSTEM,
                        item,
                        StandardCredentials.class,
                        URIRequirementBuilder.fromUri(uri).build(),
                        CredentialsMatchers.anyOf(
                                CredentialsMatchers.instanceOf(StandardUsernamePasswordCredentials.class),
                                CredentialsMatchers.instanceOf(UsernamePasswordCredentials.class)))
                .includeCurrentValue(credentialsId);
    }

    protected static FormValidation doCheckFillCredentialsId(Item item, String credentialsId, String uri) {
        if (item == null) {
            if (!Jenkins.get().hasPermission(Jenkins.ADMINISTER)) {
                return FormValidation.ok();
            }
        } else {
            if (!item.hasPermission(Item.EXTENDED_READ) && !item.hasPermission(CredentialsProvider.USE_ITEM)) {
                return FormValidation.ok();
            }
        }
        if (StringUtils.isEmpty(credentialsId)) {
            return FormValidation.ok();
        }
        if (!(findCredentials(item, credentialsId, uri).isPresent())) {
            return FormValidation.error("Cannot find currently selected credentials");
        }
        return FormValidation.ok();
    }

    protected static Optional<StandardUsernamePasswordCredentials> findCredentials(
            Item item, String credentialsId, String uri) {
        return Optional.ofNullable(CredentialsMatchers.firstOrNull(
                CredentialsProvider.lookupCredentials(
                        StandardUsernamePasswordCredentials.class,
                        item,
                        item instanceof Queue.Task ? Tasks.getAuthenticationOf((Queue.Task) item) : ACL.SYSTEM,
                        URIRequirementBuilder.fromUri(uri).build()),
                CredentialsMatchers.withId(credentialsId)));
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/EmptyFriendlyURLConverter.java
================================================
package hudson.plugins.jira;

import java.net.MalformedURLException;
import java.net.URL;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.apache.commons.beanutils.Converter;
import org.kohsuke.accmod.Restricted;
import org.kohsuke.accmod.restrictions.NoExternalUse;

/**
 * It's little hackish.
 */
@Restricted(NoExternalUse.class)
public class EmptyFriendlyURLConverter implements Converter {
    private static final Logger LOGGER = Logger.getLogger(JiraProjectProperty.class.getName());

    @Override
    public Object convert(Class aClass, Object o) {
        if (o == null || "".equals(o) || "null".equals(o)) {
            return null;
        }
        try {
            return new URL(o.toString());
        } catch (MalformedURLException e) {
            LOGGER.log(Level.WARNING, "{0} is not a valid URL", o);
            return null;
        }
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/EnvironmentExpander.java
================================================
package hudson.plugins.jira;

import hudson.EnvVars;
import hudson.model.Run;
import hudson.model.TaskListener;
import java.io.IOException;

public class EnvironmentExpander {
    public static EnvVars getEnvVars(Run<?, ?> run, TaskListener listener) {
        if (run == null || listener == null) {
            return null;
        }

        try {
            return run.getEnvironment(listener);
        } catch (IOException | InterruptedException e) {
            return null;
        }
    }

    public static String expandVariable(String variable, Run<?, ?> run, TaskListener listener) {
        EnvVars envVars = getEnvVars(run, listener);

        return expandVariable(variable, envVars);
    }

    public static String expandVariable(String variable, EnvVars envVars) {
        if (envVars == null) {
            return variable;
        }

        return envVars.expand(variable);
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/JiraBuildAction.java
================================================
package hudson.plugins.jira;

import edu.umd.cs.findbugs.annotations.NonNull;
import hudson.model.Run;
import hudson.plugins.jira.model.JiraIssue;
import java.net.URL;
import java.util.HashSet;
import java.util.Set;
import jenkins.model.RunAction2;
import org.kohsuke.stapler.export.Exported;
import org.kohsuke.stapler.export.ExportedBean;

/**
 * Jira issues related to the build.
 *
 * @author Kohsuke Kawaguchi
 */
@ExportedBean
public class JiraBuildAction implements RunAction2 {

    private final HashSet<JiraIssue> issues;
    private transient Run<?, ?> owner;

    public JiraBuildAction(@NonNull Set<JiraIssue> issues) {
        this.issues = new HashSet<>(issues);
    }

    // Leave it in place for binary compatibility.
    /**
     * @param owner the owner of this action
     * @param issues the Jira issues
     *
     * @deprecated use {@link #JiraBuildAction(java.util.Set)} instead
     */
    @Deprecated
    public JiraBuildAction(Run<?, ?> owner, @NonNull Set<JiraIssue> issues) {
        this(issues);
        // the owner will be set by #onAttached(hudson.model.Run)
    }

    @Override
    public void onAttached(Run<?, ?> r) {
        this.owner = r;
    }

    @Override
    public void onLoad(Run<?, ?> r) {
        this.owner = r;
    }

    @Override
    public String getIconFileName() {
        return null;
    }

    @Override
    public String getDisplayName() {
        return Messages.JiraBuildAction_DisplayName();
    }

    @Override
    public String getUrlName() {
        return "jira";
    }

    public Run<?, ?> getOwner() {
        return owner;
    }

    @Exported(inline = true)
    public Set<JiraIssue> getIssues() {
        return issues;
    }

    @Exported
    public String getServerURL() {
        JiraSite jiraSite = JiraSite.get(owner.getParent());
        URL url = jiraSite != null ? jiraSite.getUrl() : null;
        return url != null ? url.toString() : null;
    }

    /**
     * Finds {@link JiraIssue} whose ID matches the given one.
     *
     * @param issueID e.g. JENKINS-1234
     * @return JIRAIssue representing the issueID
     */
    public JiraIssue getIssue(String issueID) {
        for (JiraIssue issue : issues) {
            if (issue.getKey().equals(issueID)) {
                return issue;
            }
        }
        return null;
    }

    public void addIssues(Set<JiraIssue> issuesToBeSaved) {
        this.issues.addAll(issuesToBeSaved);
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/JiraCarryOverAction.java
================================================
package hudson.plugins.jira;

import hudson.Util;
import hudson.model.InvisibleAction;
import hudson.plugins.jira.model.JiraIssue;
import java.util.Arrays;
import java.util.Collection;
import java.util.Set;
import org.kohsuke.stapler.export.Exported;
import org.kohsuke.stapler.export.ExportedBean;

/**
 * Remembers Jira IDs that need to be updated later,
 * when we get a successful build.
 *
 * @author Kohsuke Kawaguchi
 */
@ExportedBean
public class JiraCarryOverAction extends InvisibleAction {
    /**
     * ','-separate IDs, for compact persistence.
     */
    private final String ids;

    public JiraCarryOverAction(Set<JiraIssue> issues) {
        StringBuilder buf = new StringBuilder();
        boolean first = true;
        for (JiraIssue issue : issues) {
            if (first) {
                first = false;
            } else {
                buf.append(",");
            }
            buf.append(issue.getKey());
        }
        this.ids = buf.toString();
    }

    @Exported
    public Collection<String> getIDs() {
        return Arrays.asList(Util.tokenize(ids, ","));
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/JiraChangeLogAnnotator.java
================================================
package hudson.plugins.jira;

import hudson.Extension;
import hudson.MarkupText;
import hudson.Util;
import hudson.model.Job;
import hudson.model.Run;
import hudson.plugins.jira.model.JiraIssue;
import hudson.scm.ChangeLogAnnotator;
import hudson.scm.ChangeLogSet.Entry;
import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.LinkedHashSet;
import java.util.Set;
import java.util.logging.Level;
import java.util.logging.Logger;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import org.apache.commons.lang3.StringUtils;

/**
 * {@link ChangeLogAnnotator} that picks up Jira issue IDs.
 *
 * @author Kohsuke Kawaguchi
 */
@Extension
public class JiraChangeLogAnnotator extends ChangeLogAnnotator {

    private static final Logger LOGGER = Logger.getLogger(JiraChangeLogAnnotator.class.getName());

    public JiraChangeLogAnnotator() {
        LOGGER.fine("JiraChangeLogAnnotator created");
    }

    @Override
    public void annotate(Run<?, ?> run, Entry change, MarkupText text) {
        JiraSite site = getSiteForProject(run.getParent());

        if (site == null) {
            LOGGER.fine("not configured with Jira site");
            return; // not configured with Jira
        }

        if (site.getDisableChangelogAnnotations()) {
            LOGGER.info("ChangeLog annotations are disabled.\n Due to this also Related Issues won't be visible.");
            return;
        }

        LOGGER.log(Level.FINE, "Using site: {0}", site.getUrl());

        // if there's any recorded detail information, try to use that, too.
        JiraBuildAction a = run.getAction(JiraBuildAction.class);

        Set<JiraIssue> issuesToBeSaved = new LinkedHashSet<>();

        Pattern pattern = site.getIssuePattern();

        if (LOGGER.isLoggable(Level.FINE)) {
            LOGGER.fine("Using issue pattern: " + pattern);
        }

        String plainText = text.getText();

        Matcher m = pattern.matcher(plainText);

        while (m.find()) {
            if (m.groupCount() >= 1) {

                String id = m.group(1);

                if (StringUtils.isNotBlank(site.credentialsId) && !hasProjectForIssue(id, site, run)) {
                    LOGGER.log(Level.INFO, "No known Jira project corresponding to id: ''{0}''", id);
                    continue;
                }

                LOGGER.log(Level.FINE, "Annotating Jira id: ''{0}''", id);

                URL url, alternativeUrl;
                try {
                    url = site.getUrl(id);
                } catch (MalformedURLException e) {
                    throw new AssertionError(e); // impossible
                }

                try {
                    alternativeUrl = site.getAlternativeUrl(id);
                    if (alternativeUrl != null) {
                        url = alternativeUrl;
                    }
                } catch (MalformedURLException e) {
                    LOGGER.log(Level.WARNING, "Failed to construct alternative URL for Jira link. " + e.getMessage());
                    // This should not fail, since we already have an URL object. Exceptions would happen elsewhere.
                    throw new AssertionError(e);
                }

                JiraIssue issue = null;
                if (a != null) {
                    issue = a.getIssue(id);
                }

                if (issue == null) {
                    try {
                        issue = site.getIssue(id);
                        if (issue != null) {
                            issuesToBeSaved.add(issue);
                        }
                    } catch (Exception e) {
                        LOGGER.log(Level.FINE, "Error getting remote issue " + id, e);
                    }
                }

                if (issue == null) {
                    text.addMarkup(m.start(1), m.end(1), "<a href='" + url + "'>", "</a>");
                } else {
                    text.addMarkup(
                            m.start(1),
                            m.end(1),
                            String.format("<a href='%s' tooltip='%s'>", url, Util.escape(issue.getSummary())),
                            "</a>");
                }

            } else {
                LOGGER.log(Level.WARNING, "The Jira pattern ''{0}'' doesn't define a capturing group!", pattern);
            }
        }

        if (!issuesToBeSaved.isEmpty()) {
            saveIssues(run, a, issuesToBeSaved);
        }
    }

    /**
     * Checks if the given Jira id will be likely to exist in this issue tracker.
     * This method checks whether the key portion is a valid key (except that
     * it can potentially use stale data). Number portion is not checked at all.
     *
     * @param id String like MNG-1234
     */
    protected boolean hasProjectForIssue(String id, JiraSite site, Run run) {
        int idx = id.indexOf('-');
        if (idx == -1) {
            return false;
        }

        Set<String> keys = site.getProjectKeys(run.getParent());
        return keys.contains(id.substring(0, idx).toUpperCase());
    }

    private void saveIssues(Run<?, ?> build, JiraBuildAction a, Set<JiraIssue> issuesToBeSaved) {
        if (a != null) {
            a.addIssues(issuesToBeSaved);
        } else {
            JiraBuildAction action = new JiraBuildAction(issuesToBeSaved);
            build.addAction(action);
        }

        try {
            build.save();
        } catch (final IOException e) {
            LOGGER.log(Level.WARNING, "Error saving updated build", e);
        }
    }

    JiraSite getSiteForProject(Job<?, ?> project) {
        return JiraSite.get(project);
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/JiraCreateIssueNotifier.java
================================================
package hudson.plugins.jira;

import static hudson.plugins.jira.JiraRestService.BUG_ISSUE_TYPE_ID;

import com.atlassian.jira.rest.client.api.RestClientException;
import com.atlassian.jira.rest.client.api.StatusCategory;
import com.atlassian.jira.rest.client.api.domain.Issue;
import com.atlassian.jira.rest.client.api.domain.IssueType;
import com.atlassian.jira.rest.client.api.domain.Priority;
import com.atlassian.jira.rest.client.api.domain.Status;
import hudson.EnvVars;
import hudson.Extension;
import hudson.Launcher;
import hudson.model.AbstractBuild;
import hudson.model.AbstractProject;
import hudson.model.BuildListener;
import hudson.model.Item;
import hudson.model.Result;
import hudson.model.TaskListener;
import hudson.tasks.BuildStepDescriptor;
import hudson.tasks.BuildStepMonitor;
import hudson.tasks.Notifier;
import hudson.tasks.Publisher;
import hudson.util.FormValidation;
import hudson.util.ListBoxModel;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.Arrays;
import java.util.List;
import java.util.logging.Logger;
import java.util.stream.Collectors;
import net.sf.json.JSONObject;
import org.apache.commons.lang3.StringUtils;
import org.kohsuke.stapler.AncestorInPath;
import org.kohsuke.stapler.DataBoundConstructor;
import org.kohsuke.stapler.QueryParameter;
import org.kohsuke.stapler.StaplerRequest2;

/**
 * When a build fails it creates jira issues.
 * Repeated failures does not create a new issue but update the existing issue
 * until the issue is closed.
 *
 * @author Rupali Behera rupali@vertisinfotech.com
 */
public class JiraCreateIssueNotifier extends Notifier {

    private static final Logger LOG = Logger.getLogger(JiraCreateIssueNotifier.class.getName());

    private String projectKey;
    private String testDescription;
    private String assignee;
    private String component;
    private Long typeId;
    private Long priorityId;
    private Integer actionIdOnSuccess;

    enum finishedStatuses {
        Closed,
        Done,
        Resolved
    }

    @DataBoundConstructor
    public JiraCreateIssueNotifier(
            String projectKey,
            String testDescription,
            String assignee,
            String component,
            Long typeId,
            Long priorityId,
            Integer actionIdOnSuccess) {
        if (projectKey == null) {
            throw new IllegalArgumentException("Project key cannot be null");
        }
        this.projectKey = projectKey;

        this.testDescription = testDescription;
        this.assignee = assignee;
        this.component = component;
        this.typeId = typeId;
        this.priorityId = priorityId;
        this.actionIdOnSuccess = actionIdOnSuccess;
    }

    public String getProjectKey() {
        return projectKey;
    }

    public void setProjectKey(String projectKey) {
        this.projectKey = projectKey;
    }

    public String getTestDescription() {
        return testDescription;
    }

    public void setTestDescription(String testDescription) {
        this.testDescription = testDescription;
    }

    public String getAssignee() {
        return assignee;
    }

    public void setAssignee(String assignee) {
        this.assignee = assignee;
    }

    public String getComponent() {
        return component;
    }

    public void setComponent(String component) {
        this.component = component;
    }

    public Long getTypeId() {
        return typeId;
    }

    public Long getPriorityId() {
        return priorityId;
    }

    public Integer getActionIdOnSuccess() {
        return actionIdOnSuccess;
    }

    @Override
    public BuildStepDescriptor<Publisher> getDescriptor() {
        return DESCRIPTOR;
    }

    @Extension
    public static final DescriptorImpl DESCRIPTOR = new DescriptorImpl();

    @Override
    public BuildStepMonitor getRequiredMonitorService() {
        return BuildStepMonitor.NONE;
    }

    @Override
    public boolean perform(AbstractBuild<?, ?> build, Launcher launcher, BuildListener listener)
            throws IOException, InterruptedException {

        String jobDirPath = build.getProject().getBuildDir().getPath();
        String filename = jobDirPath + File.separator + "issue.txt";

        EnvVars vars = build.getEnvironment(TaskListener.NULL);

        Result currentBuildResult = build.getResult();

        Result previousBuildResult = null;
        AbstractBuild<?, ?> previousBuild = build.getPreviousCompletedBuild();

        if (previousBuild != null) {
            previousBuildResult = previousBuild.getResult();
        }

        if (currentBuildResult != Result.ABORTED && previousBuild != null) {
            try {
                if (currentBuildResult == Result.FAILURE) {
                    currentBuildResultFailure(build, listener, previousBuildResult, filename, vars);
                }

                if (currentBuildResult == Result.SUCCESS) {
                    currentBuildResultSuccess(build, listener, previousBuildResult, filename, vars);
                }
            } catch (RestClientException e) {
                listener.getLogger().println(e.getMessage());
            }
        }
        return true;
    }

    /**
     * It creates a issue in the given project, with the given description,
     * assignee,components and summary.
     * The created issue ID is saved to the file at "filename".
     *
     * @param build build
     * @param filename filename
     * @return issue id
     * @throws IOException if IO fails
     * @throws InterruptedException if thread is interrupted
     */
    private Issue createJiraIssue(AbstractBuild<?, ?> build, String filename) throws IOException, InterruptedException {

        EnvVars vars = build.getEnvironment(TaskListener.NULL);
        JiraSession session = getJiraSession(build);

        String buildName = getBuildName(vars);
        String summary = String.format("Build %s failed", buildName);
        String description = String.format(
                "%s%n%nThe build %s has failed.%nFirst failed run: %s",
                (this.testDescription.equals("")) ? "No description is provided" : vars.expand(this.testDescription),
                buildName,
                getBuildDetailsString(vars));
        Iterable<String> components = Arrays.stream(component.split(","))
                .filter(s -> !StringUtils.isEmpty(s))
                .map(StringUtils::trim)
                .collect(Collectors.toList());

        Long type = typeId;
        if (type == null || type == 0) { // zero is default / invalid selection
            LOG.info("Returning default issue type id " + BUG_ISSUE_TYPE_ID);
            type = BUG_ISSUE_TYPE_ID;
        }
        Long priority = priorityId;
        if (priority != null && priority == 0) {
            priority = null; // remove invalid priority selection
        }

        Issue issue = session.createIssue(projectKey, description, assignee, components, summary, type, priority);

        writeInFile(filename, issue);
        return issue;
    }

    /**
     * Returns the status of the issue.
     *
     * @param build build
     * @param id issue key
     * @return Status of the issue
     * @throws IOException if IO fails
     */
    private Status getStatus(AbstractBuild<?, ?> build, String id) throws IOException {

        JiraSession session = getJiraSession(build);
        Issue issue = session.getIssueByKey(id);
        return issue.getStatus();
    }

    /**
     * Adds a comment to the existing issue.
     *
     * @param build build
     * @param listener listener
     * @param id issue key
     * @param comment comment text
     * @throws IOException if IO fails
     */
    private void addComment(AbstractBuild<?, ?> build, BuildListener listener, String id, String comment)
            throws IOException {
        JiraSession session = getJiraSession(build);
        session.addCommentWithoutConstrains(id, comment);
        listener.getLogger().println(String.format("[%s] Commented issue", id));
    }

    /**
     * Returns the issue id
     *
     * @param filename file from which to read the issue name
     * @return issue ID
     * @throws IOException if IO fails
     * @throws InterruptedException if thread is interrupted
     */
    private String getIssue(String filename) throws IOException, InterruptedException {
        String issueId = "";
        Path path = Paths.get(filename);
        if (Files.notExists(path)) {
            return null;
        }
        try (BufferedReader br = Files.newBufferedReader(path)) {
            String issue;

            while ((issue = br.readLine()) != null) {
                issueId = issue;
            }
            return StringUtils.trimToNull(issueId);
        } catch (FileNotFoundException e) {
            return null;
        }
    }

    JiraSite getSiteForProject(AbstractProject<?, ?> project) {
        return JiraSite.get(project);
    }

    /**
     * Returns the jira session.
     *
     * @param build build
     * @return JiraSession
     * @throws IOException if IO fails
     */
    private JiraSession getJiraSession(AbstractBuild<?, ?> build) throws IOException {

        JiraSite site = getSiteForProject(build.getProject());

        if (site == null) {
            throw new IllegalStateException(
                    "Jira site needs to be configured in the project " + build.getFullDisplayName());
        }

        JiraSession session = site.getSession(build.getProject());
        if (session == null) {
            throw new IllegalStateException("Remote access for Jira isn't configured in Jenkins");
        }

        return session;
    }

    /**
     * @param filename filename
     */
    private void deleteFile(String filename) {
        File file = new File(filename);
        if (file.exists() && !file.delete()) {
            LOG.warning("WARNING: couldn't delete file: " + filename);
        }
    }

    /**
     * Writes the issue id in the file, which is stored in the Job's directory.
     *
     * @param filename filenam
     * @param issue issue
     * @throws FileNotFoundException if file not found
     */
    private void writeInFile(String filename, Issue issue) throws IOException {
        // olamy really weird to write an empty file especially with null
        // but backward compat and unit tests assert that.....
        // can't believe such stuff has been merged......
        try (BufferedWriter bw = Files.newBufferedWriter(Paths.get(filename))) {
            bw.write(issue.getKey() == null ? "null" : issue.getKey());
        }
    }

    /**
     * when the current build fails it checks for the previous build's result,
     * creates jira issue if the result was "success" and adds comment if the result
     * was "fail".
     * It adds comment until the previously created issue is closed.
     */
    private void currentBuildResultFailure(
            AbstractBuild<?, ?> build,
            BuildListener listener,
            Result previousBuildResult,
            String filename,
            EnvVars vars)
            throws InterruptedException, IOException, RestClientException {

        if (previousBuildResult == Result.FAILURE) {
            String comment = String.format("Build is still failing.%nFailed run: %s", getBuildDetailsString(vars));

            // Get the issue-id which was filed when the previous built failed
            String issueId = getIssue(filename);
            if (issueId != null) {
                try {
                    // The status of the issue which was filed when the previous build failed
                    Status status = getStatus(build, issueId);

                    // Issue Closed, need to open new one
                    if (isDone(status)) {

                        listener.getLogger().println("The previous build also failed but the issue is closed");
                        deleteFile(filename);
                        Issue issue = createJiraIssue(build, filename);
                        LOG.info(String.format("[%s] created.", issue.getKey()));
                        listener.getLogger().println("Build failed, created Jira issue " + issue.getKey());
                    } else {
                        addComment(build, listener, issueId, comment);
                        LOG.info(String.format("[%s] The previous build also failed, comment added.", issueId));
                    }
                } catch (IOException e) {
                    LOG.warning(String.format("[%s] - error processing Jira change: %s", issueId, e.getMessage()));
                }
            }
        }

        if (previousBuildResult == Result.SUCCESS || previousBuildResult == Result.ABORTED) {
            try {
                Issue issue = createJiraIssue(build, filename);
                LOG.info(String.format("[%s] created.", issue.getKey()));
                listener.getLogger().println("Build failed, created Jira issue " + issue.getKey());
            } catch (IOException e) {
                listener.error("Error creating Jira issue : " + e.getMessage());
                LOG.warning("Error creating Jira issue\n" + e.getMessage());
            }
        }
    }

    /**
     * when the current build's result is "success",
     * it checks for the previous build's result and adds comment until the
     * previously created issue is closed.
     *
     * @param build build
     * @param previousBuildResult previous build result
     * @param filename filename
     * @param vars variables
     * @throws InterruptedException if thread isinterrupted
     * @throws IOException if IO fails
     */
    private void currentBuildResultSuccess(
            AbstractBuild<?, ?> build,
            BuildListener listener,
            Result previousBuildResult,
            String filename,
            EnvVars vars)
            throws InterruptedException, IOException {

        if (previousBuildResult == Result.FAILURE || previousBuildResult == Result.SUCCESS) {
            String comment =
                    String.format("Previously failing build now is OK.%n Passed run: %s", getBuildDetailsString(vars));
            String issueId = getIssue(filename);

            // if issue exists it will check the status and comment or delete the file
            // accordingly
            if (issueId != null) {
                try {
                    Status status = getStatus(build, issueId);

                    // if issue is in closed status
                    if (isDone(status)) {
                        LOG.info(String.format("%s is closed", issueId));
                        deleteFile(filename);
                    } else {
                        LOG.info(String.format("%s is not closed, comment was added.", issueId));
                        addComment(build, listener, issueId, comment);
                        if (actionIdOnSuccess != null && actionIdOnSuccess > 0) {
                            progressWorkflowAction(build, issueId, actionIdOnSuccess);
                        }
                    }

                } catch (IOException e) {
                    listener.error("Error updating Jira issue " + issueId + " : " + e.getMessage());
                    LOG.warning("Error updating Jira issue " + issueId + "\n" + e);
                }
            }
        }
    }

    static boolean isDone(Status status) {
        if (status.getName().equalsIgnoreCase(finishedStatuses.Closed.toString())
                || status.getName().equalsIgnoreCase(finishedStatuses.Resolved.toString())
                || status.getName().equalsIgnoreCase(finishedStatuses.Done.toString())) {
            return true;
        }

        StatusCategory category = status.getStatusCategory();
        if (category == null) {
            return false;
        }
        return "done".equals(category.getKey());
    }

    private void progressWorkflowAction(AbstractBuild<?, ?> build, String issueId, Integer actionId)
            throws IOException {
        JiraSession session = getJiraSession(build);
        session.progressWorkflowAction(issueId, actionId);
    }

    /**
     * Returns build details string in wiki format, with hyperlinks.
     *
     * @param vars environment variables
     * @return build details string
     */
    private String getBuildDetailsString(EnvVars vars) {
        final String buildURL = vars.get("BUILD_URL");
        return String.format("[%s|%s] [console log|%s]", getBuildName(vars), buildURL, buildURL.concat("console"));
    }

    /**
     * Returns build name in format BUILD#10
     *
     * @param vars environment variables
     * @return String build name
     */
    private String getBuildName(EnvVars vars) {
        final String jobName = vars.get("JOB_NAME");
        final String buildNumber = vars.get("BUILD_NUMBER");
        return String.format("%s #%s", jobName, buildNumber);
    }

    public static class DescriptorImpl extends BuildStepDescriptor<Publisher> {

        public DescriptorImpl() {
            super(JiraCreateIssueNotifier.class);
        }

        public FormValidation doCheckProjectKey(@QueryParameter String value) throws IOException {
            if (value.length() == 0) {
                return FormValidation.error("Please set the project key");
            }
            return FormValidation.ok();
        }

        public ListBoxModel doFillPriorityIdItems(@AncestorInPath final Item item) {
            ListBoxModel items = new ListBoxModel().add(""); // optional field
            List<JiraSite> sites = JiraSite.getJiraSites(item);
            for (JiraSite site : sites) {
                JiraSession session = site.getSession(item);
                if (session != null) {
                    for (Priority priority : session.getPriorities()) {
                        items.add("[" + site.getName() + "] " + priority.getName(), String.valueOf(priority.getId()));
                    }
                }
            }
            return items;
        }

        public ListBoxModel doFillTypeIdItems(@AncestorInPath final Item item) {
            ListBoxModel items = new ListBoxModel().add(""); // optional field
            List<JiraSite> sites = JiraSite.getJiraSites(item);
            for (JiraSite site : sites) {
                JiraSession session = site.getSession(item);
                if (session != null) {
                    for (IssueType type : session.getIssueTypes()) {
                        items.add("[" + site.getName() + "] " + type.getName(), String.valueOf(type.getId()));
                    }
                }
            }
            return items;
        }

        @Override
        public JiraCreateIssueNotifier newInstance(StaplerRequest2 req, JSONObject formData) throws FormException {
            return req.bindJSON(JiraCreateIssueNotifier.class, formData);
        }

        @Override
        public boolean isApplicable(Class<? extends AbstractProject> jobType) {
            return true;
        }

        @Override
        public String getDisplayName() {
            return Messages.JiraCreateIssueNotifier_DisplayName();
        }

        @Override
        public String getHelpFile() {
            return "/plugin/jira/help-jira-create-issue.html";
        }
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/JiraCreateReleaseNotes.java
================================================
package hudson.plugins.jira;

import static org.apache.commons.lang3.StringUtils.defaultIfEmpty;
import static org.apache.commons.lang3.StringUtils.isEmpty;

import hudson.EnvVars;
import hudson.Extension;
import hudson.FilePath;
import hudson.Launcher;
import hudson.model.AbstractProject;
import hudson.model.BuildListener;
import hudson.model.Job;
import hudson.model.Result;
import hudson.model.Run;
import hudson.model.TaskListener;
import hudson.tasks.BuildStepMonitor;
import hudson.tasks.BuildWrapperDescriptor;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
import jenkins.tasks.SimpleBuildWrapper;
import org.jenkinsci.Symbol;
import org.kohsuke.stapler.DataBoundConstructor;

public class JiraCreateReleaseNotes extends SimpleBuildWrapper {

    @Extension
    @Symbol("jiraCreateReleaseNotes")
    public static final class Descriptor extends BuildWrapperDescriptor {

        @Override
        public String getDisplayName() {
            return "Generate Release Notes";
        }

        @Override
        public boolean isApplicable(final AbstractProject<?, ?> item) {
            return true;
        }
    }

    public static final String DEFAULT_FILTER = "status in (Resolved, Closed)";
    public static final String DEFAULT_ENVVAR_NAME = "RELEASE_NOTES";

    private String jiraEnvironmentVariable;
    private String jiraProjectKey;
    private String jiraRelease;
    private String jiraFilter;

    // not in use anymore, as it always resets the given filter with the DEFAULT_FILTER
    public JiraCreateReleaseNotes(
            final String jiraProjectKey, final String jiraRelease, final String jiraEnvironmentVariable) {
        this(jiraProjectKey, jiraRelease, jiraEnvironmentVariable, DEFAULT_FILTER);
    }

    @DataBoundConstructor
    public JiraCreateReleaseNotes(
            final String jiraProjectKey,
            final String jiraRelease,
            final String jiraEnvironmentVariable,
            final String jiraFilter) {
        this.jiraRelease = jiraRelease;
        this.jiraProjectKey = jiraProjectKey;
        this.jiraEnvironmentVariable = defaultIfEmpty(jiraEnvironmentVariable, DEFAULT_ENVVAR_NAME);
        this.jiraFilter = defaultIfEmpty(jiraFilter, DEFAULT_FILTER);
    }

    public String getJiraEnvironmentVariable() {
        return jiraEnvironmentVariable;
    }

    public String getJiraFilter() {
        return jiraFilter;
    }

    public String getJiraProjectKey() {
        return jiraProjectKey;
    }

    public String getJiraRelease() {
        return jiraRelease;
    }

    public BuildStepMonitor getRequiredMonitorService() {
        return BuildStepMonitor.NONE;
    }

    public void setJiraEnvironmentVariable(final String jiraEnvironmentVariable) {
        this.jiraEnvironmentVariable = jiraEnvironmentVariable;
    }

    public void setJiraFilter(final String jiraFilter) {
        this.jiraFilter = jiraFilter;
    }

    public void setJiraProjectKey(final String jiraProjectKey) {
        this.jiraProjectKey = jiraProjectKey;
    }

    public void setJiraRelease(final String jiraRelease) {
        this.jiraRelease = jiraRelease;
    }

    JiraSite getSiteForProject(Job<?, ?> project) {
        return JiraSite.get(project);
    }

    @Override
    public void setUp(
            Context context,
            Run<?, ?> run,
            FilePath workspace,
            Launcher launcher,
            TaskListener listener,
            EnvVars initialEnvironment)
            throws IOException, InterruptedException {

        final JiraSite site = getSiteForProject(run.getParent());

        String realRelease = null;
        String realProjectKey = null;
        String releaseNotes = "No Release Notes";
        String realFilter = DEFAULT_FILTER;

        try {
            realRelease = run.getEnvironment(listener).expand(jiraRelease);
            realProjectKey = run.getEnvironment(listener).expand(jiraProjectKey);
            realFilter = run.getEnvironment(listener).expand(jiraFilter);

            if (isEmpty(realRelease)) {
                throw new IllegalArgumentException("No version specified");
            }
            if (isEmpty(realProjectKey)) {
                throw new IllegalArgumentException("No project specified");
            }

            if ((realRelease != null) && !realRelease.isEmpty()) {
                releaseNotes = site.getReleaseNotesForFixVersion(realProjectKey, realRelease, realFilter);
            } else {
                listener.getLogger().printf("No release version found, skipping Release Notes generation%n");
            }

        } catch (Exception e) {
            e.printStackTrace(listener.fatalError(
                    "Unable to generate release notes for Jira version %s/%s: %s", realRelease, realProjectKey, e));
            if (listener instanceof BuildListener) {
                ((BuildListener) listener).finished(Result.FAILURE);
            }
        }

        final Map<String, String> envMap = new HashMap<>();
        envMap.put(jiraEnvironmentVariable, releaseNotes);
        context.getEnv().putAll(envMap);
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/JiraEnvironmentContributingAction.java
================================================
package hudson.plugins.jira;

import edu.umd.cs.findbugs.annotations.Nullable;
import hudson.EnvVars;
import hudson.model.AbstractBuild;
import hudson.model.EnvironmentContributingAction;
import hudson.model.InvisibleAction;

/*
 * JiraEnvironmentVariableBuilder adds an instance of this class to the build to provide the environment variables
 *
 */
public class JiraEnvironmentContributingAction extends InvisibleAction implements EnvironmentContributingAction {

    public static final String ISSUES_VARIABLE_NAME = "JIRA_ISSUES";
    public static final String JIRA_URL_VARIABLE_NAME = "JIRA_URL";
    public static final String ISSUES_SIZE_VARIABLE_NAME = "JIRA_ISSUES_SIZE";

    private final String issuesList;

    private final Integer issuesSize;

    private final String jiraUrl;

    @Nullable
    public String getIssuesList() {
        return issuesList;
    }

    public Integer getNumberOfIssues() {
        return issuesSize == null ? Integer.valueOf(0) : issuesSize;
    }

    @Nullable
    public String getJiraUrl() {
        return jiraUrl;
    }

    public JiraEnvironmentContributingAction(String issuesList, Integer issuesSize, String jiraUrl) {
        this.issuesList = issuesList;
        this.issuesSize = issuesSize;
        this.jiraUrl = jiraUrl;
    }

    @Override
    public void buildEnvVars(AbstractBuild<?, ?> ab, EnvVars ev) {
        if (ev != null) {
            ev.put(ISSUES_VARIABLE_NAME, getIssuesList());
            ev.put(ISSUES_SIZE_VARIABLE_NAME, getNumberOfIssues().toString());
            ev.put(JIRA_URL_VARIABLE_NAME, getJiraUrl());
        }
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/JiraEnvironmentVariableBuilder.java
================================================
package hudson.plugins.jira;

import com.atlassian.jira.rest.client.api.RestClientException;
import hudson.Extension;
import hudson.Launcher;
import hudson.model.AbstractBuild;
import hudson.model.AbstractProject;
import hudson.model.BuildListener;
import hudson.plugins.jira.selector.AbstractIssueSelector;
import hudson.plugins.jira.selector.DefaultIssueSelector;
import hudson.tasks.BuildStepDescriptor;
import hudson.tasks.Builder;
import java.io.IOException;
import java.util.Set;
import jenkins.model.Jenkins;
import org.apache.commons.lang3.StringUtils;
import org.kohsuke.stapler.DataBoundConstructor;

/**
 * Adds Jira related environment variables to the build
 */
public class JiraEnvironmentVariableBuilder extends Builder {

    private AbstractIssueSelector issueSelector;

    @DataBoundConstructor
    public JiraEnvironmentVariableBuilder(AbstractIssueSelector issueSelector) {
        this.issueSelector = issueSelector;
    }

    public AbstractIssueSelector getIssueSelector() {
        AbstractIssueSelector uis = this.issueSelector;
        if (uis == null) {
            uis = new DefaultIssueSelector();
        }
        return (this.issueSelector = uis);
    }

    JiraSite getSiteForProject(AbstractProject<?, ?> project) {
        return JiraSite.get(project);
    }

    @Override
    public boolean perform(AbstractBuild<?, ?> build, Launcher launcher, BuildListener listener)
            throws InterruptedException, IOException {

        JiraSite site = getSiteForProject(build.getProject());

        if (site == null) {
            listener.getLogger().println(Messages.JiraEnvironmentVariableBuilder_NoJiraSite());
            return false;
        }

        Set<String> ids;
        try {
            ids = getIssueSelector().findIssueIds(build, site, listener);
        } catch (RestClientException e) {
            listener.getLogger().println(e.getMessage());
            return false;
        }

        String idList = StringUtils.join(ids, ",");
        Integer idListSize = ids.size();

        listener.getLogger()
                .println(Messages.JiraEnvironmentVariableBuilder_Updating(
                        JiraEnvironmentContributingAction.ISSUES_VARIABLE_NAME, idList));
        listener.getLogger()
                .println(Messages.JiraEnvironmentVariableBuilder_Updating(
                        JiraEnvironmentContributingAction.ISSUES_SIZE_VARIABLE_NAME, idListSize));

        build.addAction(new JiraEnvironmentContributingAction(idList, idListSize, site.getName()));

        return true;
    }

    /**
     * Descriptor for {@link JiraEnvironmentVariableBuilder}.
     */
    @Extension
    public static final class DescriptorImpl extends BuildStepDescriptor<Builder> {

        @Override
        public boolean isApplicable(Class<? extends AbstractProject> klass) {
            return true;
        }

        @Override
        public String getDisplayName() {
            return Messages.JiraEnvironmentVariableBuilder_DisplayName();
        }

        public boolean hasIssueSelectors() {
            return Jenkins.get().getDescriptorList(AbstractIssueSelector.class).size() > 0;
        }
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/JiraFolderProperty.java
================================================
package hudson.plugins.jira;

import com.cloudbees.hudson.plugins.folder.AbstractFolder;
import com.cloudbees.hudson.plugins.folder.AbstractFolderProperty;
import com.cloudbees.hudson.plugins.folder.AbstractFolderPropertyDescriptor;
import edu.umd.cs.findbugs.annotations.NonNull;
import hudson.Extension;
import hudson.model.ItemGroup;
import java.util.Collections;
import java.util.List;
import org.kohsuke.stapler.DataBoundConstructor;
import org.kohsuke.stapler.DataBoundSetter;

/**
 * Provides folder level Jira configuration.
 */
public class JiraFolderProperty extends AbstractFolderProperty<AbstractFolder<?>> {
    /**
     * Hold the Jira sites configuration.
     */
    private List<JiraSite> sites = Collections.emptyList();

    /**
     * Constructor.
     */
    @DataBoundConstructor
    public JiraFolderProperty() {}

    /**
     * Return the Jira sites.
     *
     * @return the Jira sites
     */
    public JiraSite[] getSites() {
        return sites.toArray(new JiraSite[0]);
    }

    /**
     * @param site the Jira site
     * @deprecated use {@link #setSites(List)} instead
     */
    @Deprecated
    public void setSites(JiraSite site) {
        sites.add(site);
    }

    @DataBoundSetter
    public void setSites(List<JiraSite> sites) {
        this.sites = sites;
    }

    /**
     * @deprecated use {@link JiraSite#getSitesFromFolders(ItemGroup)}
     */
    @Deprecated
    public static List<JiraSite> getSitesFromFolders(ItemGroup itemGroup) {
        return JiraSite.getSitesFromFolders(itemGroup);
    }

    /**
     * Descriptor class.
     */
    @Extension
    public static class DescriptorImpl extends AbstractFolderPropertyDescriptor {

        @NonNull
        @Override
        public String getDisplayName() {
            return Messages.JiraFolderProperty_DisplayName();
        }
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/JiraGlobalConfiguration.java
================================================
package hudson.plugins.jira;

import edu.umd.cs.findbugs.annotations.NonNull;
import edu.umd.cs.findbugs.annotations.SuppressFBWarnings;
import hudson.Extension;
import hudson.util.PersistedList;
import java.util.List;
import jenkins.model.GlobalConfiguration;
import jenkins.model.Jenkins;
import org.kohsuke.stapler.DataBoundSetter;

@Extension
public class JiraGlobalConfiguration extends GlobalConfiguration {

    @NonNull
    public static JiraGlobalConfiguration get() {
        return (JiraGlobalConfiguration) Jenkins.get().getDescriptorOrDie(JiraGlobalConfiguration.class);
    }

    @SuppressFBWarnings(value = "PA_PUBLIC_PRIMITIVE_ATTRIBUTE", justification = "Backwards compatibility")
    public List<JiraSite> sites = new PersistedList<>(this);

    public JiraGlobalConfiguration() {
        load();
    }

    public List<JiraSite> getSites() {
        return sites;
    }

    @DataBoundSetter
    public void setSites(List<JiraSite> sites) {
        this.sites = sites;
        save();
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/JiraIssueMigrator.java
================================================
package hudson.plugins.jira;

import hudson.Extension;
import hudson.Launcher;
import hudson.model.AbstractBuild;
import hudson.model.AbstractProject;
import hudson.model.BuildListener;
import hudson.model.Result;
import hudson.tasks.BuildStepDescriptor;
import hudson.tasks.BuildStepMonitor;
import hudson.tasks.Notifier;
import hudson.tasks.Publisher;
import net.sf.json.JSONObject;
import org.kohsuke.stapler.DataBoundConstructor;
import org.kohsuke.stapler.StaplerRequest2;

public class JiraIssueMigrator extends Notifier {

    private static final long serialVersionUID = 6909671291180081586L;

    private String jiraProjectKey;
    private String jiraRelease;
    private String jiraReplaceVersion;
    private String jiraQuery;
    private boolean addRelease;

    @DataBoundConstructor
    public JiraIssueMigrator(
            String jiraProjectKey,
            String jiraRelease,
            String jiraQuery,
            String jiraReplaceVersion,
            boolean addRelease) {
        this.jiraRelease = jiraRelease;
        this.jiraProjectKey = jiraProjectKey;
        this.jiraQuery = jiraQuery;
        this.jiraReplaceVersion = jiraReplaceVersion;
        this.addRelease = addRelease;
    }

    public String getJiraRelease() {
        return jiraRelease;
    }

    public void setJiraRelease(String jiraRelease) {
        this.jiraRelease = jiraRelease;
    }

    public String getJiraProjectKey() {
        return jiraProjectKey;
    }

    public void setJiraProjectKey(String jiraProjectKey) {
        this.jiraProjectKey = jiraProjectKey;
    }

    public String getJiraQuery() {
        return jiraQuery;
    }

    public void setJiraQuery(String jiraQuery) {
        this.jiraQuery = jiraQuery;
    }

    public String getJiraReplaceVersion() {
        return jiraReplaceVersion;
    }

    public void setJiraReplaceVersion(String jiraReplaceVersion) {
        this.jiraReplaceVersion = jiraReplaceVersion;
    }

    public boolean isAddRelease() {
        return addRelease;
    }

    public void setAddRelease(boolean addRelease) {
        this.addRelease = addRelease;
    }

    @Override
    public BuildStepDescriptor<Publisher> getDescriptor() {
        return DESCRIPTOR;
    }

    @Extension
    public static final DescriptorImpl DESCRIPTOR = new DescriptorImpl();

    @Override
    public boolean perform(AbstractBuild<?, ?> build, Launcher launcher, BuildListener listener) {
        String realRelease = null;
        String realReplace = null;
        String realQuery = "";
        String realProjectKey = null;
        try {
            realRelease = build.getEnvironment(listener).expand(jiraRelease);
            realReplace = build.getEnvironment(listener).expand(jiraReplaceVersion);
            realProjectKey = build.getEnvironment(listener).expand(jiraProjectKey);

            if (realRelease == null || realRelease.isEmpty()) {
                throw new IllegalArgumentException("Release is Empty");
            }

            if (realProjectKey == null || realProjectKey.isEmpty()) {
                throw new IllegalArgumentException("No project specified");
            }

            realQuery = build.getEnvironment(listener).expand(jiraQuery);
            if (realQuery == null || realQuery.isEmpty()) {
                throw new IllegalArgumentException("JQL query is Empty");
            }

            JiraSite site = getJiraSiteForProject(build.getProject());

            if (addRelease) {
                site.addFixVersionToIssue(realProjectKey, realRelease, realQuery);
            } else {
                if (realReplace == null || realReplace.isEmpty()) {
                    site.migrateIssuesToFixVersion(realProjectKey, realRelease, realQuery);
                } else {
                    site.replaceFixVersion(realProjectKey, realReplace, realRelease, realQuery);
                }
            }
        } catch (Exception e) {
            e.printStackTrace(
                    listener.fatalError("Unable to release jira version %s/%s: %s", realRelease, realProjectKey, e));
            listener.finished(Result.FAILURE);
            return false;
        }
        return true;
    }

    JiraSite getJiraSiteForProject(AbstractProject<?, ?> project) {
        return JiraSite.get(project);
    }

    @Override
    public BuildStepMonitor getRequiredMonitorService() {
        return BuildStepMonitor.NONE;
    }

    public static class DescriptorImpl extends BuildStepDescriptor<Publisher> {

        public DescriptorImpl() {
            super(JiraIssueMigrator.class);
        }

        @Override
        public JiraIssueMigrator newInstance(StaplerRequest2 req, JSONObject formData) throws FormException {
            return req.bindJSON(JiraIssueMigrator.class, formData);
        }

        @Override
        public boolean isApplicable(Class<? extends AbstractProject> jobType) {
            return true;
        }

        @Override
        public String getDisplayName() {
            return Messages.JiraReleaseVersionMigrator_DisplayName();
        }

        @Override
        public String getHelpFile() {
            return "/plugin/jira/help-release-migrate.html";
        }
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/JiraIssueUpdateBuilder.java
================================================
/*
 * Copyright 2012 MeetMe, Inc.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package hudson.plugins.jira;

import com.atlassian.jira.rest.client.api.RestClientException;
import hudson.EnvVars;
import hudson.Extension;
import hudson.Util;
import hudson.model.*;
import hudson.tasks.BuildStepDescriptor;
import hudson.tasks.Builder;
import hudson.util.FormValidation;
import java.io.IOException;
import jenkins.tasks.SimpleBuildStep;
import org.apache.commons.lang3.StringUtils;
import org.jenkinsci.Symbol;
import org.kohsuke.stapler.DataBoundConstructor;
import org.kohsuke.stapler.QueryParameter;

/**
 * Build step that will mass-update all issues matching a JQL query, using the specified workflow
 * action name (e.g., "Resolve Issue", "Close Issue").
 *
 * @author Joe Hansche jhansche@myyearbook.com
 */
public class JiraIssueUpdateBuilder extends Builder implements SimpleBuildStep {
    private final String jqlSearch;
    private final String workflowActionName;
    private final String comment;

    @DataBoundConstructor
    public JiraIssueUpdateBuilder(String jqlSearch, String workflowActionName, String comment) {
        this.jqlSearch = Util.fixEmptyAndTrim(jqlSearch);
        this.workflowActionName = Util.fixEmptyAndTrim(workflowActionName);
        this.comment = Util.fixEmptyAndTrim(comment);
    }

    /**
     * @return the jql
     */
    public String getJqlSearch() {
        return jqlSearch;
    }

    /**
     * @return the workflowActionName
     */
    public String getWorkflowActionName() {
        return workflowActionName;
    }

    /**
     * @return the comment
     */
    public String getComment() {
        return comment;
    }

    JiraSite getSiteForJob(Job<?, ?> job) {
        return JiraSite.get(job);
    }

    /**
     * Performs the actual update based on job configuration.
     */
    @Override
    public void perform(Run<?, ?> run, EnvVars env, TaskListener listener) throws InterruptedException, IOException {
        String realComment = Util.fixEmptyAndTrim(env.expand(comment));
        String realJql = Util.fixEmptyAndTrim(env.expand(jqlSearch));
        String realWorkflowActionName = Util.fixEmptyAndTrim(env.expand(workflowActionName));

        JiraSite site = getSiteForJob(run.getParent());

        if (site == null) {
            listener.getLogger().println(Messages.NoJiraSite());
            run.setResult(Result.FAILURE);
            return;
        }

        if (StringUtils.isNotEmpty(realWorkflowActionName)) {
            listener.getLogger().println(Messages.JiraIssueUpdateBuilder_UpdatingWithAction(realWorkflowActionName));
        }

        listener.getLogger().println("[Jira] JQL: " + realJql);

        try {
            if (!site.progressMatchingIssues(realJql, realWorkflowActionName, realComment, listener.getLogger())) {
                listener.getLogger().println(Messages.JiraIssueUpdateBuilder_SomeIssuesFailed());
                run.setResult(Result.UNSTABLE);
            }
        } catch (RestClientException e) {
            listener.getLogger().println(e.getMessage());
            run.setResult(Result.FAILURE);
        }
    }

    @Override
    public boolean requiresWorkspace() {
        return false;
    }

    @Override
    public DescriptorImpl getDescriptor() {
        return (DescriptorImpl) super.getDescriptor();
    }

    /**
     * Descriptor for {@link JiraIssueUpdateBuilder}.
     */
    @Extension
    @Symbol("jiraExecuteWorkflow")
    public static final class DescriptorImpl extends BuildStepDescriptor<Builder> {
        /**
         * Performs on-the-fly validation of the form field 'Jql'.
         *
         * @param value This parameter receives the value that the user has typed.
         * @return Indicates the outcome of the validation. This is sent to the browser.
         */
        public FormValidation doCheckJqlSearch(@QueryParameter String value) {
            if (value.length() == 0) {
                return FormValidation.error(Messages.JiraIssueUpdateBuilder_NoJqlSearch());
            }

            return FormValidation.ok();
        }

        public FormValidation doCheckWorkflowActionName(@QueryParameter String value) {
            if (Util.fixNull(value).trim().length() == 0) {
                return FormValidation.warning(Messages.JiraIssueUpdateBuilder_NoWorkflowAction());
            }

            return FormValidation.ok();
        }

        @Override
        public boolean isApplicable(Class<? extends AbstractProject> klass) {
            return true;
        }

        /**
         * This human readable name is used in the configuration screen.
         */
        @Override
        public String getDisplayName() {
            return Messages.JiraIssueUpdateBuilder_DisplayName();
        }
    }
}


================================================
FILE: src/main/java/hudson/plugins/jira/JiraIssueUpdater.java
================================================
package hudson.plugins.jira;

import hudson.EnvVars;
import hudson.Extension;
import hudson.Launcher;
import hudson.matrix.MatrixAggregatable;
import hudson.matrix.MatrixAggregator;
import hudson.matrix.MatrixBuild;
import hudson.matrix.MatrixRun;
import hudson.model.AbstractBuild;
import hudson.model.AbstractProject;
import hudson.model.BuildListener;
import hudson.model.Run;
import hudson.model.TaskListener;
import hudson.plugins.jira.selector.AbstractIssueSelector;
import hudson.plugins.jira.selector.DefaultIssueSelector;
import hudson.scm.SCM;
import hudson.tasks.BuildStepDescriptor;
import hudson.tasks.BuildStepMonitor;
import hudson.tasks.Publisher;
import hudson.tasks.Recorder;
import java.io.IOException;
import java.io.PrintStream;
import java.util.ArrayList;
import java.util.List;
import jenkins.model.Jenkins;
import jenkins.tasks.SimpleBuildStep;
import org.jenkinsci.Symbol;
import org.kohsuke.stapler.DataBoundConstructor;

/**
 * Parses build changelog for Jira issue IDs and then
 * updates Jira issues accordingly.
 *
 * @author Kohsuke Kawaguchi
 */
public class JiraIssueUpdater extends Recorder implements MatrixAggregatable, SimpleBuildStep {

    private AbstractIssueSelector issueSelector;
    private SCM scm;
    private List<String> labels;

    @DataBoundConstructor
    public JiraIssueUpdater(AbstractIssueSelector issueSelector, SCM scm, List<String> labels) {
        this.issueSelector = issueSelector;
        this.scm = scm;
        if (labels != null) {
            this.labels = labels;
        } else {
            this.labels = new ArrayList();
        }
    }

    @Override
    public void perform(Run<?, ?> run, EnvVars env, TaskListener listener) throws InterruptedException, IOException {
        /
Download .txt
gitextract_wo4b4tn0/

├── .git-blame-ignore-revs
├── .github/
│   ├── CODEOWNERS
│   ├── FUNDING.yml
│   ├── ISSUE_TEMPLATE/
│   │   ├── 1-report-bug.yml
│   │   ├── 2-feature-request.yml
│   │   ├── 3-documentation.yml
│   │   └── config.yml
│   ├── pull_request_template.md
│   ├── release-drafter.yml
│   ├── renovate.json
│   └── workflows/
│       ├── crowdin.yml
│       ├── jenkins-security-scan.yml
│       ├── release-drafter.yml
│       └── sonarcloud.yml
├── .gitignore
├── .mvn/
│   ├── extensions.xml
│   └── maven.config
├── .pre-commit-config.yaml
├── CONTRIBUTING.md
├── Jenkinsfile
├── LICENSE.md
├── README.md
├── crowdin.yml
├── docker-compose.yml
├── docs/
│   ├── .nojekyll
│   ├── README.md
│   ├── _sidebar.md
│   ├── changelog.md
│   ├── features.md
│   ├── index.html
│   ├── system-properties.md
│   ├── troubleshooting.md
│   └── usage-examples.md
├── pom.xml
└── src/
    ├── main/
    │   ├── java/
    │   │   ├── com/
    │   │   │   └── atlassian/
    │   │   │       └── httpclient/
    │   │   │           ├── apache/
    │   │   │           │   └── httpcomponents/
    │   │   │           │       ├── ApacheAsyncHttpClient.java
    │   │   │           │       ├── CommonBuilder.java
    │   │   │           │       ├── CompletableFuturePromiseHttpPromiseAsyncClient.java
    │   │   │           │       ├── DefaultHttpClientFactory.java
    │   │   │           │       ├── DefaultMessage.java
    │   │   │           │       ├── DefaultRequest.java
    │   │   │           │       ├── DefaultResponse.java
    │   │   │           │       ├── EntityByteArrayInputStream.java
    │   │   │           │       ├── Headers.java
    │   │   │           │       ├── MavenUtils.java
    │   │   │           │       ├── PromiseHttpAsyncClient.java
    │   │   │           │       ├── RedirectStrategy.java
    │   │   │           │       └── RequestEntityEffect.java
    │   │   │           └── base/
    │   │   │               └── event/
    │   │   │                   ├── AbstractHttpRequestEvent.java
    │   │   │                   ├── HttpRequestCompletedEvent.java
    │   │   │                   └── HttpRequestFailedEvent.java
    │   │   └── hudson/
    │   │       └── plugins/
    │   │           └── jira/
    │   │               ├── CredentialsHelper.java
    │   │               ├── EmptyFriendlyURLConverter.java
    │   │               ├── EnvironmentExpander.java
    │   │               ├── JiraBuildAction.java
    │   │               ├── JiraCarryOverAction.java
    │   │               ├── JiraChangeLogAnnotator.java
    │   │               ├── JiraCreateIssueNotifier.java
    │   │               ├── JiraCreateReleaseNotes.java
    │   │               ├── JiraEnvironmentContributingAction.java
    │   │               ├── JiraEnvironmentVariableBuilder.java
    │   │               ├── JiraFolderProperty.java
    │   │               ├── JiraGlobalConfiguration.java
    │   │               ├── JiraIssueMigrator.java
    │   │               ├── JiraIssueUpdateBuilder.java
    │   │               ├── JiraIssueUpdater.java
    │   │               ├── JiraJobAction.java
    │   │               ├── JiraMailAddressResolver.java
    │   │               ├── JiraProjectProperty.java
    │   │               ├── JiraReleaseVersionUpdater.java
    │   │               ├── JiraReleaseVersionUpdaterBuilder.java
    │   │               ├── JiraRestService.java
    │   │               ├── JiraSession.java
    │   │               ├── JiraSessionFactory.java
    │   │               ├── JiraSite.java
    │   │               ├── JiraVersionCreator.java
    │   │               ├── JiraVersionCreatorBuilder.java
    │   │               ├── RunScmChangeExtractor.java
    │   │               ├── Updater.java
    │   │               ├── VersionCreator.java
    │   │               ├── VersionReleaser.java
    │   │               ├── auth/
    │   │               │   └── BearerHttpAuthenticationHandler.java
    │   │               ├── extension/
    │   │               │   ├── ExtendedAsynchronousJiraRestClient.java
    │   │               │   ├── ExtendedAsynchronousMyPermissionsRestClient.java
    │   │               │   ├── ExtendedAsynchronousVersionRestClient.java
    │   │               │   ├── ExtendedJiraRestClient.java
    │   │               │   ├── ExtendedMyPermissionsRestClient.java
    │   │               │   ├── ExtendedVersion.java
    │   │               │   ├── ExtendedVersionInput.java
    │   │               │   ├── ExtendedVersionInputJsonGenerator.java
    │   │               │   ├── ExtendedVersionJsonParser.java
    │   │               │   └── ExtendedVersionRestClient.java
    │   │               ├── listissuesparameter/
    │   │               │   ├── JiraIssueParameterDefinition.java
    │   │               │   └── JiraIssueParameterValue.java
    │   │               ├── model/
    │   │               │   ├── JiraIssue.java
    │   │               │   ├── JiraIssueField.java
    │   │               │   └── JiraVersion.java
    │   │               ├── pipeline/
    │   │               │   ├── CommentStep.java
    │   │               │   ├── IssueFieldUpdateStep.java
    │   │               │   ├── IssueSelectorStep.java
    │   │               │   └── SearchIssuesStep.java
    │   │               ├── selector/
    │   │               │   ├── AbstractIssueSelector.java
    │   │               │   ├── DefaultIssueSelector.java
    │   │               │   ├── ExplicitIssueSelector.java
    │   │               │   ├── JqlIssueSelector.java
    │   │               │   └── perforce/
    │   │               │       ├── JobIssueSelector.java
    │   │               │       └── P4JobIssueSelector.java
    │   │               └── versionparameter/
    │   │                   ├── JiraVersionParameterDefinition.java
    │   │                   ├── JiraVersionParameterValue.java
    │   │                   └── VersionComparator.java
    │   ├── resources/
    │   │   ├── atlassian-httpclient-plugin-0.23.0.pom
    │   │   ├── hudson/
    │   │   │   └── plugins/
    │   │   │       └── jira/
    │   │   │           ├── JiraBuildAction/
    │   │   │           │   └── summary.jelly
    │   │   │           ├── JiraCreateIssueNotifier/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-actionIdOnSuccess.html
    │   │   │           │   ├── help-assignee.html
    │   │   │           │   ├── help-component.html
    │   │   │           │   ├── help-priorityId.html
    │   │   │           │   ├── help-projectKey.html
    │   │   │           │   ├── help-testDescription.html
    │   │   │           │   └── help-typeId.html
    │   │   │           ├── JiraCreateReleaseNotes/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-jiraEnvironmentVariable.html
    │   │   │           │   ├── help-jiraFilter.html
    │   │   │           │   ├── help-jiraProjectKey.html
    │   │   │           │   └── help-jiraRelease.html
    │   │   │           ├── JiraEnvironmentVariableBuilder/
    │   │   │           │   ├── config.jelly
    │   │   │           │   └── help.html
    │   │   │           ├── JiraFolderProperty/
    │   │   │           │   └── config.jelly
    │   │   │           ├── JiraGlobalConfiguration/
    │   │   │           │   └── config.jelly
    │   │   │           ├── JiraIssueMigrator/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-addRelease.html
    │   │   │           │   ├── help-jiraProjectKey.html
    │   │   │           │   ├── help-jiraQuery.html
    │   │   │           │   ├── help-jiraRelease.html
    │   │   │           │   └── help-jiraReplaceVersion.html
    │   │   │           ├── JiraIssueUpdateBuilder/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-comment.html
    │   │   │           │   ├── help-jqlSearch.html
    │   │   │           │   ├── help-workflowActionName.html
    │   │   │           │   └── help.html
    │   │   │           ├── JiraIssueUpdater/
    │   │   │           │   └── config.jelly
    │   │   │           ├── JiraProjectProperty/
    │   │   │           │   └── config.jelly
    │   │   │           ├── JiraReleaseVersionUpdater/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-jiraDescription.html
    │   │   │           │   ├── help-jiraProjectKey.html
    │   │   │           │   └── help-jiraRelease.html
    │   │   │           ├── JiraReleaseVersionUpdaterBuilder/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-jiraDescription.html
    │   │   │           │   ├── help-jiraProjectKey.html
    │   │   │           │   └── help-jiraRelease.html
    │   │   │           ├── JiraSite/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── config.properties
    │   │   │           │   ├── config_de.properties
    │   │   │           │   ├── config_fr.properties
    │   │   │           │   ├── config_it.properties
    │   │   │           │   ├── config_ja.properties
    │   │   │           │   ├── config_nl.properties
    │   │   │           │   ├── config_pl.properties
    │   │   │           │   ├── help-alternativeUrl.html
    │   │   │           │   ├── help-appendChangeTimestamp.html
    │   │   │           │   ├── help-credentialsId.html
    │   │   │           │   ├── help-credentialsId_de.html
    │   │   │           │   ├── help-credentialsId_fr.html
    │   │   │           │   ├── help-credentialsId_ja.html
    │   │   │           │   ├── help-dateTimePattern.html
    │   │   │           │   ├── help-disableChangelogAnnotations.html
    │   │   │           │   ├── help-groupVisibility.html
    │   │   │           │   ├── help-maxIssuesFromJqlSearch.html
    │   │   │           │   ├── help-readTimeout.html
    │   │   │           │   ├── help-recordScmChanges.html
    │   │   │           │   ├── help-recordScmChanges_fr.html
    │   │   │           │   ├── help-recordScmChanges_ja.html
    │   │   │           │   ├── help-roleVisibility.html
    │   │   │           │   ├── help-supportsWikiStyleComment.html
    │   │   │           │   ├── help-supportsWikiStyleComment_de.html
    │   │   │           │   ├── help-supportsWikiStyleComment_fr.html
    │   │   │           │   ├── help-supportsWikiStyleComment_ja.html
    │   │   │           │   ├── help-threadExecutorNumber.html
    │   │   │           │   ├── help-timeout.html
    │   │   │           │   ├── help-updateJiraIssueForAllStatus.html
    │   │   │           │   ├── help-url.html
    │   │   │           │   ├── help-url_de.html
    │   │   │           │   ├── help-url_fr.html
    │   │   │           │   ├── help-url_ja.html
    │   │   │           │   ├── help-useHTTPAuth.html
    │   │   │           │   ├── help-userPattern.html
    │   │   │           │   ├── help-userPattern_de.html
    │   │   │           │   ├── help-userPattern_fr.html
    │   │   │           │   └── help-userPattern_ja.html
    │   │   │           ├── JiraVersionCreator/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-failIfAlreadyExists.html
    │   │   │           │   ├── help-jiraProjectKey.html
    │   │   │           │   └── help-jiraVersion.html
    │   │   │           ├── JiraVersionCreatorBuilder/
    │   │   │           │   ├── config.jelly
    │   │   │           │   ├── help-failIfAlreadyExists.html
    │   │   │           │   ├── help-jiraProjectKey.html
    │   │   │           │   └── help-jiraVersion.html
    │   │   │           ├── MavenJiraIssueUpdater/
    │   │   │           │   └── config.jelly
    │   │   │           ├── Messages.properties
    │   │   │           ├── Messages_de.properties
    │   │   │           ├── Messages_fr.properties
    │   │   │           ├── Messages_it.properties
    │   │   │           ├── Messages_ja.properties
    │   │   │           ├── Messages_pl.properties
    │   │   │           ├── listissuesparameter/
    │   │   │           │   ├── JiraIssueParameterDefinition/
    │   │   │           │   │   ├── config.jelly
    │   │   │           │   │   ├── help-altSummaryFields.html
    │   │   │           │   │   ├── help-jiraIssueFilter.html
    │   │   │           │   │   └── index.jelly
    │   │   │           │   └── JiraIssueParameterValue/
    │   │   │           │       └── value.jelly
    │   │   │           ├── pipeline/
    │   │   │           │   ├── CommentStep/
    │   │   │           │   │   └── config.jelly
    │   │   │           │   ├── IssueFieldUpdateStep/
    │   │   │           │   │   ├── config.jelly
    │   │   │           │   │   ├── help-fieldId.html
    │   │   │           │   │   └── help.html
    │   │   │           │   ├── IssueSelectorStep/
    │   │   │           │   │   └── config.jelly
    │   │   │           │   └── SearchIssuesStep/
    │   │   │           │       └── config.jelly
    │   │   │           ├── selector/
    │   │   │           │   ├── DefaultIssueSelector/
    │   │   │           │   │   └── config.jelly
    │   │   │           │   ├── ExplicitIssueSelector/
    │   │   │           │   │   └── config.jelly
    │   │   │           │   ├── JqlIssueSelector/
    │   │   │           │   │   └── config.jelly
    │   │   │           │   └── perforce/
    │   │   │           │       ├── P4JobIssueSelector/
    │   │   │           │       │   └── config.jelly
    │   │   │           │       └── PerforceJobIssueSelector/
    │   │   │           │           └── config.jelly
    │   │   │           └── versionparameter/
    │   │   │               ├── JiraVersionParameterDefinition/
    │   │   │               │   ├── config.jelly
    │   │   │               │   ├── help-jiraProjectKey.html
    │   │   │               │   ├── help-jiraReleasePattern.html
    │   │   │               │   ├── help-jiraShowReleased.html
    │   │   │               │   └── index.jelly
    │   │   │               └── JiraVersionParameterValue/
    │   │   │                   └── value.jelly
    │   │   └── index.jelly
    │   └── webapp/
    │       ├── help-jira-create-issue.html
    │       ├── help-release-migrate.html
    │       ├── help-release.html
    │       ├── help-version-create.html
    │       ├── help.html
    │       ├── help_de.html
    │       ├── help_fr.html
    │       └── help_ja.html
    ├── spotbugs/
    │   └── excludesFilter.xml
    └── test/
        ├── java/
        │   ├── JiraConfig.java
        │   ├── JiraTester.java
        │   ├── JiraTesterBearerAuth.java
        │   ├── com/
        │   │   └── atlassian/
        │   │       └── httpclient/
        │   │           └── apache/
        │   │               └── httpcomponents/
        │   │                   ├── ApacheAsyncHttpClientTest.java
        │   │                   └── CompletableFuturePromiseHttpPromiseAsyncClientTest.java
        │   └── hudson/
        │       └── plugins/
        │           └── jira/
        │               ├── BuildListenerResultMethodMock.java
        │               ├── ChangingWorkflowTest.java
        │               ├── CliParameterTest.java
        │               ├── ConfigAsCodeTest.java
        │               ├── CredentialsHelperTest.java
        │               ├── DescriptorImplTest.java
        │               ├── EmptyFriendlyURLConverterTest.java
        │               ├── EnvironmentExpanderTest.java
        │               ├── JiraBuildActionTest.java
        │               ├── JiraChangeLogAnnotatorTest.java
        │               ├── JiraCreateIssueNotifierTest.java
        │               ├── JiraCreateReleaseNotesTest.java
        │               ├── JiraEnvironmentContributingActionTest.java
        │               ├── JiraEnvironmentVariableBuilderTest.java
        │               ├── JiraFolderPropertyTest.java
        │               ├── JiraGlobalConfigurationSaveTest.java
        │               ├── JiraGlobalConfigurationTest.java
        │               ├── JiraIssueMigratorTest.java
        │               ├── JiraIssueParameterDefResultTest.java
        │               ├── JiraIssueUpdateBuilderTest.java
        │               ├── JiraIssueUpdaterTest.java
        │               ├── JiraJobActionTest.java
        │               ├── JiraProjectPropertyTest.java
        │               ├── JiraReleaseVersionUpdateBuilderTest.java
        │               ├── JiraRestServiceProxyTest.java
        │               ├── JiraRestServiceTest.java
        │               ├── JiraSessionTest.java
        │               ├── JiraSiteSecurity1029Test.java
        │               ├── JiraSiteTest.java
        │               ├── JiraVersionCreatorBuilderTest.java
        │               ├── MailResolverDisabledTest.java
        │               ├── MailResolverWithExtensionTest.java
        │               ├── MockAffectedFile.java
        │               ├── UnmaskMailTest.java
        │               ├── UpdaterTest.java
        │               ├── VersionCreatorTest.java
        │               ├── VersionReleaserTest.java
        │               ├── auth/
        │               │   ├── BearerHttpAuthenticationHandlerTest.java
        │               │   └── JiraRestServiceBearerAuthTest.java
        │               ├── listissuesparameter/
        │               │   ├── JiraIssueParameterDefinitionTest.java
        │               │   └── JiraIssueParameterTest.java
        │               ├── pipeline/
        │               │   ├── CommentStepTest.java
        │               │   ├── IssueFieldUpdateStepTest.java
        │               │   ├── IssueSelectorStepTest.java
        │               │   └── SearchIssuesStepTest.java
        │               ├── selector/
        │               │   ├── DefaultIssueSelectorTest.java
        │               │   ├── ExplicitIssueSelectorTest.java
        │               │   ├── JqlIssueSelectorTest.java
        │               │   └── perforce/
        │               │       ├── JobIssueSelectorTest.java
        │               │       └── P4JobIssueSelectorTest.java
        │               └── versionparameter/
        │                   ├── JiraReleaseVersionParameterTest.java
        │                   ├── JiraVersionParameterDefinitionTest.java
        │                   └── VersionComparatorTest.java
        └── resources/
            ├── hudson/
            │   └── plugins/
            │       └── jira/
            │           ├── JiraBuildActionTest/
            │           │   └── binaryCompatibility/
            │           │       ├── config.xml
            │           │       └── jobs/
            │           │           └── project/
            │           │               ├── builds/
            │           │               │   └── 2/
            │           │               │       └── build.xml
            │           │               └── config.xml
            │           ├── multiple-sites.yml
            │           ├── oldJiraProjectProperty.xml
            │           └── single-site.yml
            └── jira.properties
Download .txt
SYMBOL INDEX (1297 symbols across 133 files)

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/ApacheAsyncHttpClient.java
  class ApacheAsyncHttpClient (line 93) | public final class ApacheAsyncHttpClient<C> implements HttpClient, Dispo...
    method ApacheAsyncHttpClient (line 107) | public ApacheAsyncHttpClient(
    method ApacheAsyncHttpClient (line 114) | public ApacheAsyncHttpClient(
    method ApacheAsyncHttpClient (line 126) | public ApacheAsyncHttpClient(
    method createClientBuilder (line 147) | private HttpAsyncClientBuilder createClientBuilder() throws IOReactorE...
    class JenkinsProxyRoutePlanner (line 235) | private class JenkinsProxyRoutePlanner extends DefaultRoutePlanner {
      method JenkinsProxyRoutePlanner (line 239) | public JenkinsProxyRoutePlanner(HttpHost proxy, List<Pattern> nonPro...
      method determineProxy (line 245) | @Override
      method bypassProxy (line 251) | private boolean bypassProxy(String host) {
    method getRegistry (line 261) | private Registry<SchemeIOSessionStrategy> getRegistry(final HttpClient...
    method getSelfSignedVerifier (line 288) | private X509HostnameVerifier getSelfSignedVerifier() {
    method getFallbackRegistry (line 313) | private Registry<SchemeIOSessionStrategy> getFallbackRegistry(final Ge...
    method getUserAgent (line 321) | private String getUserAgent(HttpClientOptions options) {
    method execute (line 327) | @Override
    method doExecute (line 336) | private ResponsePromise doExecute(final Request request) {
    method publishEvent (line 399) | private void publishEvent(Request request, long requestDuration, int s...
    method publishEvent (line 417) | private void publishEvent(Request request, long requestDuration, Throw...
    method getPromiseHttpAsyncClient (line 426) | private PromiseHttpAsyncClient getPromiseHttpAsyncClient(Request reque...
    method translate (line 443) | private Response translate(HttpResponse httpResponse) throws IOExcepti...
    method destroy (line 461) | @Override
    method flushCacheByUriPattern (line 475) | @Override
    class NoOpThreadLocalContextManager (line 480) | private static final class NoOpThreadLocalContextManager<C> implements...
      method getThreadLocalContext (line 481) | @Override
      method setThreadLocalContext (line 486) | @Override
      method clearThreadLocalContext (line 489) | @Override
    class DefaultApplicationNameSupplier (line 493) | private static final class DefaultApplicationNameSupplier implements S...
      method DefaultApplicationNameSupplier (line 496) | public DefaultApplicationNameSupplier(ApplicationProperties applicat...
      method get (line 500) | @Override
    class EventConsumerFunction (line 510) | private static class EventConsumerFunction implements Function<Object,...
      method EventConsumerFunction (line 513) | public EventConsumerFunction(EventPublisher eventPublisher) {
      method apply (line 517) | @Override
    method split (line 526) | private static String[] split(final String s) {
    method newRequest (line 533) | @Override
    method newRequest (line 538) | @Override
    method newRequest (line 543) | @Override
    method newRequest (line 551) | @Override
    method newRequest (line 556) | @Override
    method transformation (line 561) | @Override

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/CommonBuilder.java
  class CommonBuilder (line 8) | public class CommonBuilder<T> implements Common<CommonBuilder<T>> {
    method setHeader (line 12) | @Override
    method setHeaders (line 18) | @Override
    method setEntity (line 24) | @Override
    method setEntityStream (line 36) | @Override
    method setContentCharset (line 42) | @Override
    method setContentType (line 48) | @Override
    method setEntityStream (line 54) | @Override
    method getEntityStream (line 61) | public InputStream getEntityStream() {
    method getHeaders (line 65) | public Headers getHeaders() {

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/CompletableFuturePromiseHttpPromiseAsyncClient.java
  class CompletableFuturePromiseHttpPromiseAsyncClient (line 20) | final class CompletableFuturePromiseHttpPromiseAsyncClient<C> implements...
    method CompletableFuturePromiseHttpPromiseAsyncClient (line 27) | CompletableFuturePromiseHttpPromiseAsyncClient(
    method execute (line 36) | @Override
    method closeClient (line 69) | private void closeClient() {
    method runInContext (line 77) | static <C> void runInContext(
    class ThreadLocalContextAwareFutureCallback (line 94) | private abstract static class ThreadLocalContextAwareFutureCallback<C>...
      method ThreadLocalContextAwareFutureCallback (line 99) | private ThreadLocalContextAwareFutureCallback(ThreadLocalContextMana...
      method doCompleted (line 105) | abstract void doCompleted(HttpResponse response);
      method doFailed (line 107) | abstract void doFailed(Exception ex);
      method doCancelled (line 109) | abstract void doCancelled();
      method completed (line 111) | @Override
      method failed (line 117) | @Override
      method cancelled (line 122) | @Override
    class ThreadLocalDelegateExecutor (line 128) | private static final class ThreadLocalDelegateExecutor<C> implements E...
      method ThreadLocalDelegateExecutor (line 132) | ThreadLocalDelegateExecutor(ThreadLocalContextManager<C> manager, Ex...
      method execute (line 137) | @Override
    class ThreadLocalDelegateRunnable (line 143) | private static final class ThreadLocalDelegateRunnable<C> implements R...
      method ThreadLocalDelegateRunnable (line 149) | ThreadLocalDelegateRunnable(ThreadLocalContextManager<C> manager, Ru...
      method run (line 156) | @Override

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/DefaultHttpClientFactory.java
  class DefaultHttpClientFactory (line 13) | public final class DefaultHttpClientFactory implements HttpClientFactory...
    method DefaultHttpClientFactory (line 20) | public DefaultHttpClientFactory(
    method create (line 29) | @Override
    method create (line 34) | @Override
    method dispose (line 39) | @Override
    method doCreate (line 46) | private HttpClient doCreate(HttpClientOptions options, ThreadLocalCont...
    method destroy (line 60) | @Override

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/DefaultMessage.java
  class DefaultMessage (line 17) | abstract class DefaultMessage implements Message {
    method DefaultMessage (line 23) | public DefaultMessage(final Headers headers, final InputStream entityS...
    method getContentType (line 29) | @Override
    method getContentCharset (line 34) | @Override
    method getAccept (line 39) | public String getAccept() {
    method getEntityStream (line 43) | @Override
    method getEntity (line 49) | @Override
    method hasEntity (line 90) | @Override
    method hasReadEntity (line 95) | @Override
    method getHeaders (line 100) | @Override
    method getHeader (line 105) | @Override
    method validate (line 110) | public Message validate() {
    method checkRead (line 117) | private void checkRead() throws IllegalStateException {
    method checkValidSize (line 126) | private void checkValidSize() throws IllegalArgumentException {

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/DefaultRequest.java
  class DefaultRequest (line 23) | public class DefaultRequest extends DefaultMessage implements Request {
    method DefaultRequest (line 30) | private DefaultRequest(
    method builder (line 46) | public static DefaultRequestBuilder builder(HttpClient httpClient) {
    method getMethod (line 50) | @Override
    method getUri (line 55) | @Override
    method getAccept (line 60) | @Override
    method getAttribute (line 65) | @Override
    method getAttributes (line 70) | @Override
    method getContentLength (line 75) | @Override
    method isCacheDisabled (line 80) | @Override
    method validate (line 85) | @Override
    class DefaultRequestBuilder (line 109) | public static class DefaultRequestBuilder implements Request.Builder {
      method DefaultRequestBuilder (line 119) | public DefaultRequestBuilder(final HttpClient httpClient) {
      method setUri (line 127) | @Override
      method setAccept (line 133) | @Override
      method setCacheDisabled (line 139) | @Override
      method setAttribute (line 145) | @Override
      method setAttributes (line 151) | @Override
      method setEntity (line 157) | @Override
      method setHeader (line 168) | @Override
      method setHeaders (line 174) | @Override
      method setEntity (line 180) | @Override
      method setEntityStream (line 187) | @Override
      method setContentCharset (line 193) | @Override
      method setContentType (line 199) | @Override
      method setEntityStream (line 205) | @Override
      method setContentLength (line 212) | @Override
      method build (line 221) | @Override
      method get (line 233) | @Override
      method post (line 238) | @Override
      method put (line 243) | @Override
      method delete (line 248) | @Override
      method options (line 253) | @Override
      method head (line 258) | @Override
      method trace (line 263) | @Override
      method execute (line 268) | @Override
      method setMethod (line 275) | public void setMethod(final Method method) {

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/DefaultResponse.java
  class DefaultResponse (line 10) | public final class DefaultResponse extends DefaultMessage implements Res...
    method DefaultResponse (line 15) | public DefaultResponse(
    method builder (line 22) | public static DefaultResponseBuilder builder() {
    method getStatusCode (line 26) | @Override
    method getStatusText (line 31) | @Override
    method isInformational (line 36) | @Override
    method isSuccessful (line 41) | @Override
    method isOk (line 46) | @Override
    method isCreated (line 51) | @Override
    method isNoContent (line 56) | @Override
    method isRedirection (line 61) | @Override
    method isSeeOther (line 66) | @Override
    method isNotModified (line 71) | @Override
    method isClientError (line 76) | @Override
    method isBadRequest (line 81) | @Override
    method isUnauthorized (line 86) | @Override
    method isForbidden (line 91) | @Override
    method isNotFound (line 96) | @Override
    method isConflict (line 101) | @Override
    method isServerError (line 106) | @Override
    method isInternalServerError (line 111) | @Override
    method isServiceUnavailable (line 116) | @Override
    method isError (line 121) | @Override
    method isNotSuccessful (line 126) | @Override
    method getContentLength (line 131) | @Override
    class DefaultResponseBuilder (line 154) | public static class DefaultResponseBuilder implements Builder {
      method DefaultResponseBuilder (line 161) | private DefaultResponseBuilder() {
      method setContentType (line 165) | @Override
      method setContentCharset (line 171) | @Override
      method setHeaders (line 177) | @Override
      method setHeader (line 183) | @Override
      method setEntity (line 189) | @Override
      method setEntityStream (line 195) | @Override
      method setEntityStream (line 202) | @Override
      method setStatusText (line 208) | @Override
      method setStatusCode (line 214) | @Override
      method setMaxEntitySize (line 220) | public DefaultResponseBuilder setMaxEntitySize(long maxEntitySize) {
      method build (line 225) | @Override

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/EntityByteArrayInputStream.java
  class EntityByteArrayInputStream (line 5) | public class EntityByteArrayInputStream extends ByteArrayInputStream {
    method EntityByteArrayInputStream (line 8) | public EntityByteArrayInputStream(byte[] bytes) {
    method getBytes (line 13) | public byte[] getBytes() {

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/Headers.java
  class Headers (line 10) | public class Headers {
    method Headers (line 15) | private Headers(Map<String, String> headers, String contentCharset, St...
    method getContentCharset (line 21) | public String getContentCharset() {
    method getContentType (line 25) | public String getContentType() {
    method getHeaders (line 29) | public Map<String, String> getHeaders() {
    method getHeader (line 37) | public String getHeader(final String name) {
    method buildContentType (line 47) | private String buildContentType() {
    class Builder (line 55) | public static class Builder implements Buildable<Headers> {
      method setHeaders (line 60) | public Builder setHeaders(Map<String, String> headers) {
      method setHeader (line 68) | public Builder setHeader(String name, String value) {
      method setContentLength (line 77) | public Builder setContentLength(long contentLength) {
      method setContentCharset (line 85) | public Builder setContentCharset(String contentCharset) {
      method setContentType (line 91) | public Builder setContentType(String contentType) {
      method parseContentType (line 96) | private void parseContentType(String value) {
      method build (line 115) | @Override
    class Names (line 121) | public static class Names {
      method Names (line 125) | private Names() {}

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/MavenUtils.java
  class MavenUtils (line 10) | final class MavenUtils {
    method getVersion (line 15) | static String getVersion(String groupId, String artifactId) {
    method getPomFilePath (line 30) | private static String getPomFilePath(String groupId, String artifactId) {

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/PromiseHttpAsyncClient.java
  type PromiseHttpAsyncClient (line 8) | interface PromiseHttpAsyncClient {
    method execute (line 9) | Promise<HttpResponse> execute(HttpUriRequest request, HttpContext cont...

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/RedirectStrategy.java
  class RedirectStrategy (line 18) | public class RedirectStrategy extends DefaultRedirectStrategy {
    method isRedirectable (line 28) | @Override
    method getRedirect (line 38) | @Override

FILE: src/main/java/com/atlassian/httpclient/apache/httpcomponents/RequestEntityEffect.java
  class RequestEntityEffect (line 15) | public class RequestEntityEffect implements Effect<HttpRequestBase> {
    method RequestEntityEffect (line 18) | public RequestEntityEffect(final Request request) {
    method apply (line 22) | @Override
    method getHttpEntity (line 32) | private HttpEntity getHttpEntity(final Request request) {

FILE: src/main/java/com/atlassian/httpclient/base/event/AbstractHttpRequestEvent.java
  class AbstractHttpRequestEvent (line 5) | abstract class AbstractHttpRequestEvent {
    method AbstractHttpRequestEvent (line 14) | public AbstractHttpRequestEvent(
    method AbstractHttpRequestEvent (line 23) | public AbstractHttpRequestEvent(
    method getUrl (line 32) | public String getUrl() {
    method getStatusCode (line 36) | public int getStatusCode() {
    method getError (line 40) | public String getError() {
    method getRequestDuration (line 44) | public long getRequestDuration() {
    method getProperties (line 48) | public Map<String, String> getProperties() {

FILE: src/main/java/com/atlassian/httpclient/base/event/HttpRequestCompletedEvent.java
  class HttpRequestCompletedEvent (line 5) | public final class HttpRequestCompletedEvent extends AbstractHttpRequest...
    method HttpRequestCompletedEvent (line 6) | public HttpRequestCompletedEvent(

FILE: src/main/java/com/atlassian/httpclient/base/event/HttpRequestFailedEvent.java
  class HttpRequestFailedEvent (line 5) | public final class HttpRequestFailedEvent extends AbstractHttpRequestEve...
    method HttpRequestFailedEvent (line 6) | public HttpRequestFailedEvent(
    method HttpRequestFailedEvent (line 11) | public HttpRequestFailedEvent(

FILE: src/main/java/hudson/plugins/jira/CredentialsHelper.java
  class CredentialsHelper (line 37) | public class CredentialsHelper {
    method lookupSystemCredentials (line 40) | @CheckForNull
    method migrateCredentials (line 56) | protected static StandardUsernamePasswordCredentials migrateCredentials(
    method doFillCredentialsIdItems (line 89) | protected static ListBoxModel doFillCredentialsIdItems(Item item, Stri...
    method doCheckFillCredentialsId (line 112) | protected static FormValidation doCheckFillCredentialsId(Item item, St...
    method findCredentials (line 131) | protected static Optional<StandardUsernamePasswordCredentials> findCre...

FILE: src/main/java/hudson/plugins/jira/EmptyFriendlyURLConverter.java
  class EmptyFriendlyURLConverter (line 14) | @Restricted(NoExternalUse.class)
    method convert (line 18) | @Override

FILE: src/main/java/hudson/plugins/jira/EnvironmentExpander.java
  class EnvironmentExpander (line 8) | public class EnvironmentExpander {
    method getEnvVars (line 9) | public static EnvVars getEnvVars(Run<?, ?> run, TaskListener listener) {
    method expandVariable (line 21) | public static String expandVariable(String variable, Run<?, ?> run, Ta...
    method expandVariable (line 27) | public static String expandVariable(String variable, EnvVars envVars) {

FILE: src/main/java/hudson/plugins/jira/JiraBuildAction.java
  class JiraBuildAction (line 18) | @ExportedBean
    method JiraBuildAction (line 24) | public JiraBuildAction(@NonNull Set<JiraIssue> issues) {
    method JiraBuildAction (line 35) | @Deprecated
    method onAttached (line 41) | @Override
    method onLoad (line 46) | @Override
    method getIconFileName (line 51) | @Override
    method getDisplayName (line 56) | @Override
    method getUrlName (line 61) | @Override
    method getOwner (line 66) | public Run<?, ?> getOwner() {
    method getIssues (line 70) | @Exported(inline = true)
    method getServerURL (line 75) | @Exported
    method getIssue (line 88) | public JiraIssue getIssue(String issueID) {
    method addIssues (line 97) | public void addIssues(Set<JiraIssue> issuesToBeSaved) {

FILE: src/main/java/hudson/plugins/jira/JiraCarryOverAction.java
  class JiraCarryOverAction (line 18) | @ExportedBean
    method JiraCarryOverAction (line 25) | public JiraCarryOverAction(Set<JiraIssue> issues) {
    method getIDs (line 39) | @Exported

FILE: src/main/java/hudson/plugins/jira/JiraChangeLogAnnotator.java
  class JiraChangeLogAnnotator (line 27) | @Extension
    method JiraChangeLogAnnotator (line 32) | public JiraChangeLogAnnotator() {
    method annotate (line 36) | @Override
    method hasProjectForIssue (line 140) | protected boolean hasProjectForIssue(String id, JiraSite site, Run run) {
    method saveIssues (line 150) | private void saveIssues(Run<?, ?> build, JiraBuildAction a, Set<JiraIs...
    method getSiteForProject (line 165) | JiraSite getSiteForProject(Job<?, ?> project) {

FILE: src/main/java/hudson/plugins/jira/JiraCreateIssueNotifier.java
  class JiraCreateIssueNotifier (line 52) | public class JiraCreateIssueNotifier extends Notifier {
    type finishedStatuses (line 64) | enum finishedStatuses {
    method JiraCreateIssueNotifier (line 70) | @DataBoundConstructor
    method getProjectKey (line 92) | public String getProjectKey() {
    method setProjectKey (line 96) | public void setProjectKey(String projectKey) {
    method getTestDescription (line 100) | public String getTestDescription() {
    method setTestDescription (line 104) | public void setTestDescription(String testDescription) {
    method getAssignee (line 108) | public String getAssignee() {
    method setAssignee (line 112) | public void setAssignee(String assignee) {
    method getComponent (line 116) | public String getComponent() {
    method setComponent (line 120) | public void setComponent(String component) {
    method getTypeId (line 124) | public Long getTypeId() {
    method getPriorityId (line 128) | public Long getPriorityId() {
    method getActionIdOnSuccess (line 132) | public Integer getActionIdOnSuccess() {
    method getDescriptor (line 136) | @Override
    method getRequiredMonitorService (line 144) | @Override
    method perform (line 149) | @Override
    method createJiraIssue (line 194) | private Issue createJiraIssue(AbstractBuild<?, ?> build, String filena...
    method getStatus (line 235) | private Status getStatus(AbstractBuild<?, ?> build, String id) throws ...
    method addComment (line 251) | private void addComment(AbstractBuild<?, ?> build, BuildListener liste...
    method getIssue (line 266) | private String getIssue(String filename) throws IOException, Interrupt...
    method getSiteForProject (line 284) | JiraSite getSiteForProject(AbstractProject<?, ?> project) {
    method getJiraSession (line 295) | private JiraSession getJiraSession(AbstractBuild<?, ?> build) throws I...
    method deleteFile (line 315) | private void deleteFile(String filename) {
    method writeInFile (line 329) | private void writeInFile(String filename, Issue issue) throws IOExcept...
    method currentBuildResultFailure (line 344) | private void currentBuildResultFailure(
    method currentBuildResultSuccess (line 404) | private void currentBuildResultSuccess(
    method isDone (line 443) | static boolean isDone(Status status) {
    method progressWorkflowAction (line 457) | private void progressWorkflowAction(AbstractBuild<?, ?> build, String ...
    method getBuildDetailsString (line 469) | private String getBuildDetailsString(EnvVars vars) {
    method getBuildName (line 480) | private String getBuildName(EnvVars vars) {
    class DescriptorImpl (line 486) | public static class DescriptorImpl extends BuildStepDescriptor<Publish...
      method DescriptorImpl (line 488) | public DescriptorImpl() {
      method doCheckProjectKey (line 492) | public FormValidation doCheckProjectKey(@QueryParameter String value...
      method doFillPriorityIdItems (line 499) | public ListBoxModel doFillPriorityIdItems(@AncestorInPath final Item...
      method doFillTypeIdItems (line 513) | public ListBoxModel doFillTypeIdItems(@AncestorInPath final Item ite...
      method newInstance (line 527) | @Override
      method isApplicable (line 532) | @Override
      method getDisplayName (line 537) | @Override
      method getHelpFile (line 542) | @Override

FILE: src/main/java/hudson/plugins/jira/JiraCreateReleaseNotes.java
  class JiraCreateReleaseNotes (line 25) | public class JiraCreateReleaseNotes extends SimpleBuildWrapper {
    class Descriptor (line 27) | @Extension
      method getDisplayName (line 31) | @Override
      method isApplicable (line 36) | @Override
    method JiraCreateReleaseNotes (line 51) | public JiraCreateReleaseNotes(
    method JiraCreateReleaseNotes (line 56) | @DataBoundConstructor
    method getJiraEnvironmentVariable (line 68) | public String getJiraEnvironmentVariable() {
    method getJiraFilter (line 72) | public String getJiraFilter() {
    method getJiraProjectKey (line 76) | public String getJiraProjectKey() {
    method getJiraRelease (line 80) | public String getJiraRelease() {
    method getRequiredMonitorService (line 84) | public BuildStepMonitor getRequiredMonitorService() {
    method setJiraEnvironmentVariable (line 88) | public void setJiraEnvironmentVariable(final String jiraEnvironmentVar...
    method setJiraFilter (line 92) | public void setJiraFilter(final String jiraFilter) {
    method setJiraProjectKey (line 96) | public void setJiraProjectKey(final String jiraProjectKey) {
    method setJiraRelease (line 100) | public void setJiraRelease(final String jiraRelease) {
    method getSiteForProject (line 104) | JiraSite getSiteForProject(Job<?, ?> project) {
    method setUp (line 108) | @Override

FILE: src/main/java/hudson/plugins/jira/JiraEnvironmentContributingAction.java
  class JiraEnvironmentContributingAction (line 13) | public class JiraEnvironmentContributingAction extends InvisibleAction i...
    method getIssuesList (line 25) | @Nullable
    method getNumberOfIssues (line 30) | public Integer getNumberOfIssues() {
    method getJiraUrl (line 34) | @Nullable
    method JiraEnvironmentContributingAction (line 39) | public JiraEnvironmentContributingAction(String issuesList, Integer is...
    method buildEnvVars (line 45) | @Override

FILE: src/main/java/hudson/plugins/jira/JiraEnvironmentVariableBuilder.java
  class JiraEnvironmentVariableBuilder (line 22) | public class JiraEnvironmentVariableBuilder extends Builder {
    method JiraEnvironmentVariableBuilder (line 26) | @DataBoundConstructor
    method getIssueSelector (line 31) | public AbstractIssueSelector getIssueSelector() {
    method getSiteForProject (line 39) | JiraSite getSiteForProject(AbstractProject<?, ?> project) {
    method perform (line 43) | @Override
    class DescriptorImpl (line 80) | @Extension
      method isApplicable (line 83) | @Override
      method getDisplayName (line 88) | @Override
      method hasIssueSelectors (line 93) | public boolean hasIssueSelectors() {

FILE: src/main/java/hudson/plugins/jira/JiraFolderProperty.java
  class JiraFolderProperty (line 17) | public class JiraFolderProperty extends AbstractFolderProperty<AbstractF...
    method JiraFolderProperty (line 26) | @DataBoundConstructor
    method getSites (line 34) | public JiraSite[] getSites() {
    method setSites (line 42) | @Deprecated
    method setSites (line 47) | @DataBoundSetter
    method getSitesFromFolders (line 55) | @Deprecated
    class DescriptorImpl (line 63) | @Extension
      method getDisplayName (line 66) | @NonNull

FILE: src/main/java/hudson/plugins/jira/JiraGlobalConfiguration.java
  class JiraGlobalConfiguration (line 12) | @Extension
    method get (line 15) | @NonNull
    method JiraGlobalConfiguration (line 23) | public JiraGlobalConfiguration() {
    method getSites (line 27) | public List<JiraSite> getSites() {
    method setSites (line 31) | @DataBoundSetter

FILE: src/main/java/hudson/plugins/jira/JiraIssueMigrator.java
  class JiraIssueMigrator (line 17) | public class JiraIssueMigrator extends Notifier {
    method JiraIssueMigrator (line 27) | @DataBoundConstructor
    method getJiraRelease (line 41) | public String getJiraRelease() {
    method setJiraRelease (line 45) | public void setJiraRelease(String jiraRelease) {
    method getJiraProjectKey (line 49) | public String getJiraProjectKey() {
    method setJiraProjectKey (line 53) | public void setJiraProjectKey(String jiraProjectKey) {
    method getJiraQuery (line 57) | public String getJiraQuery() {
    method setJiraQuery (line 61) | public void setJiraQuery(String jiraQuery) {
    method getJiraReplaceVersion (line 65) | public String getJiraReplaceVersion() {
    method setJiraReplaceVersion (line 69) | public void setJiraReplaceVersion(String jiraReplaceVersion) {
    method isAddRelease (line 73) | public boolean isAddRelease() {
    method setAddRelease (line 77) | public void setAddRelease(boolean addRelease) {
    method getDescriptor (line 81) | @Override
    method perform (line 89) | @Override
    method getJiraSiteForProject (line 133) | JiraSite getJiraSiteForProject(AbstractProject<?, ?> project) {
    method getRequiredMonitorService (line 137) | @Override
    class DescriptorImpl (line 142) | public static class DescriptorImpl extends BuildStepDescriptor<Publish...
      method DescriptorImpl (line 144) | public DescriptorImpl() {
      method newInstance (line 148) | @Override
      method isApplicable (line 153) | @Override
      method getDisplayName (line 158) | @Override
      method getHelpFile (line 163) | @Override

FILE: src/main/java/hudson/plugins/jira/JiraIssueUpdateBuilder.java
  class JiraIssueUpdateBuilder (line 40) | public class JiraIssueUpdateBuilder extends Builder implements SimpleBui...
    method JiraIssueUpdateBuilder (line 45) | @DataBoundConstructor
    method getJqlSearch (line 55) | public String getJqlSearch() {
    method getWorkflowActionName (line 62) | public String getWorkflowActionName() {
    method getComment (line 69) | public String getComment() {
    method getSiteForJob (line 73) | JiraSite getSiteForJob(Job<?, ?> job) {
    method perform (line 80) | @Override
    method requiresWorkspace (line 111) | @Override
    method getDescriptor (line 116) | @Override
    class DescriptorImpl (line 124) | @Extension
      method doCheckJqlSearch (line 133) | public FormValidation doCheckJqlSearch(@QueryParameter String value) {
      method doCheckWorkflowActionName (line 141) | public FormValidation doCheckWorkflowActionName(@QueryParameter Stri...
      method isApplicable (line 149) | @Override
      method getDisplayName (line 157) | @Override

FILE: src/main/java/hudson/plugins/jira/JiraIssueUpdater.java
  class JiraIssueUpdater (line 37) | public class JiraIssueUpdater extends Recorder implements MatrixAggregat...
    method JiraIssueUpdater (line 43) | @DataBoundConstructor
    method perform (line 54) | @Override
    method requiresWorkspace (line 72) | @Override
    method getRequiredMonitorService (line 77) | @Override
    method getDescriptor (line 82) | @Override
    method getIssueSelector (line 87) | public AbstractIssueSelector getIssueSelector() {
    method getScm (line 95) | public SCM getScm() {
    method getLabels (line 99) | public List<String> getLabels() {
    method createAggregator (line 106) | @Override
    class DescriptorImpl (line 119) | @Symbol("jiraCommentIssues")
      method DescriptorImpl (line 121) | private DescriptorImpl() {
      method getDisplayName (line 125) | @Override
      method getHelpFile (line 131) | @Override
      method isApplicable (line 136) | @Override
      method hasIssueSelectors (line 142) | public boolean hasIssueSelectors() {

FILE: src/main/java/hudson/plugins/jira/JiraJobAction.java
  class JiraJobAction (line 33) | @ExportedBean
    method JiraJobAction (line 41) | @DataBoundConstructor
    method getIssue (line 50) | @Exported
    method getServerURL (line 58) | @Exported
    method setAction (line 73) | public static void setAction(@NonNull Job job, @NonNull JiraSite site)...
    method getIconFileName (line 107) | @Override
    method getDisplayName (line 112) | @Override
    method getUrlName (line 117) | @Override
    class RunListenerImpl (line 122) | @Extension
      method onStarted (line 124) | @Override

FILE: src/main/java/hudson/plugins/jira/JiraMailAddressResolver.java
  class JiraMailAddressResolver (line 18) | @Extension
    method findMailAddressFor (line 29) | @Override
    method unmaskEmail (line 69) | static String unmaskEmail(String email) {

FILE: src/main/java/hudson/plugins/jira/JiraProjectProperty.java
  class JiraProjectProperty (line 24) | public class JiraProjectProperty extends JobProperty<Job<?, ?>> {
    method JiraProjectProperty (line 33) | @DataBoundConstructor
    method getSite (line 51) | @Nullable
    class DescriptorImpl (line 71) | @Extension
      method isApplicable (line 76) | @Override
      method getDisplayName (line 82) | @Override
      method setSites (line 92) | @Deprecated
      method getSites (line 102) | @Deprecated
      method doFillSiteNameItems (line 107) | @SuppressWarnings("unused") // Used by stapler
      method migrate (line 120) | @SuppressWarnings("unused") // Used to start migration after all ext...
      method readResolve (line 129) | @SuppressWarnings("deprecation") // Migrate configuration

FILE: src/main/java/hudson/plugins/jira/JiraReleaseVersionUpdater.java
  class JiraReleaseVersionUpdater (line 23) | @Deprecated
    method JiraReleaseVersionUpdater (line 31) | @Deprecated
    method JiraReleaseVersionUpdater (line 37) | @DataBoundConstructor
    method getJiraRelease (line 44) | public String getJiraRelease() {
    method setJiraRelease (line 48) | public void setJiraRelease(String jiraRelease) {
    method getJiraProjectKey (line 52) | public String getJiraProjectKey() {
    method setJiraProjectKey (line 56) | public void setJiraProjectKey(String jiraProjectKey) {
    method getJiraDescription (line 60) | public String getJiraDescription() {
    method setJiraDescription (line 64) | public void setJiraDescription(String jiraDescription) {
    method getDescriptor (line 68) | @Override
    method perform (line 76) | @Override
    method getRequiredMonitorService (line 82) | @Override
    class DescriptorImpl (line 87) | public static class DescriptorImpl extends BuildStepDescriptor<Publish...
      method DescriptorImpl (line 89) | public DescriptorImpl() {
      method newInstance (line 93) | @Override
      method isApplicable (line 98) | @Override
      method getDisplayName (line 103) | @Override
      method getHelpFile (line 108) | @Override

FILE: src/main/java/hudson/plugins/jira/JiraReleaseVersionUpdaterBuilder.java
  class JiraReleaseVersionUpdaterBuilder (line 20) | public class JiraReleaseVersionUpdaterBuilder extends Builder implements...
    method JiraReleaseVersionUpdaterBuilder (line 29) | @Deprecated
    method JiraReleaseVersionUpdaterBuilder (line 35) | @DataBoundConstructor
    method getJiraRelease (line 42) | public String getJiraRelease() {
    method setJiraRelease (line 46) | public void setJiraRelease(String jiraRelease) {
    method getJiraProjectKey (line 50) | public String getJiraProjectKey() {
    method setJiraProjectKey (line 54) | public void setJiraProjectKey(String jiraProjectKey) {
    method getJiraDescription (line 58) | public String getJiraDescription() {
    method setJiraDescription (line 62) | public void setJiraDescription(String jiraDescription) {
    method perform (line 66) | @Override
    method requiresWorkspace (line 71) | @Override
    method getDescriptor (line 76) | @Override
    class DescriptorImpl (line 81) | @Symbol("jiraMarkVersionReleased")
      method DescriptorImpl (line 84) | private DescriptorImpl() {
      method isApplicable (line 88) | @Override
      method getDisplayName (line 93) | @Override
      method getHelpFile (line 99) | @Override
      method newInstance (line 104) | @Override

FILE: src/main/java/hudson/plugins/jira/JiraRestService.java
  class JiraRestService (line 83) | public class JiraRestService {
    method JiraRestService (line 109) | @Deprecated
    method JiraRestService (line 114) | public JiraRestService(
    method JiraRestService (line 131) | public JiraRestService(URI uri, ExtendedJiraRestClient jiraRestClient,...
    method buildBaseApiPath (line 140) | private String buildBaseApiPath(URI uri) {
    method addComment (line 154) | public void addComment(String issueId, String commentBody, String grou...
    method getIssue (line 180) | public Issue getIssue(String issueKey) {
    method getIssueTypes (line 199) | public List<IssueType> getIssueTypes() {
    method getPriorities (line 216) | public List<Priority> getPriorities() {
    method getProjectsKeys (line 233) | public List<String> getProjectsKeys() {
    method getIssuesFromJqlSearch (line 249) | public List<Issue> getIssuesFromJqlSearch(String jqlSearch, Integer ma...
    method getVersions (line 272) | public List<ExtendedVersion> getVersions(String projectKey) {
    method addVersion (line 309) | public Version addVersion(String projectKey, String versionName) {
    method releaseVersion (line 324) | public void releaseVersion(String projectKey, ExtendedVersion version) {
    method createIssue (line 353) | @Deprecated
    method createIssue (line 359) | public BasicIssue createIssue(
    method getUser (line 406) | public User getUser(String username) {
    method updateIssue (line 424) | public void updateIssue(String issueKey, List<Version> fixVersions) {
    method setIssueLabels (line 436) | public void setIssueLabels(String issueKey, List<String> labels) {
    method setIssueFields (line 450) | public void setIssueFields(String issueKey, List<JiraIssueField> field...
    method progressWorkflowAction (line 467) | public Issue progressWorkflowAction(String issueKey, Integer actionId) {
    method getAvailableActions (line 482) | public List<Transition> getAvailableActions(String issueKey) {
    method getStatuses (line 496) | public List<Status> getStatuses() {
    method getComponents (line 508) | public List<Component> getComponents(String projectKey) {
    method buildGetRequest (line 545) | private Request buildGetRequest(URI uri) {
    method timeoutInMilliseconds (line 565) | protected int timeoutInMilliseconds() {
    method getBaseApiPath (line 569) | public String getBaseApiPath() {
    method getMyPermissions (line 576) | public Permissions getMyPermissions() {

FILE: src/main/java/hudson/plugins/jira/JiraSession.java
  class JiraSession (line 41) | public class JiraSession {
    method JiraSession (line 55) | JiraSession(JiraSite site, JiraRestService jiraRestService) {
    method getProjectKeys (line 66) | public Set<String> getProjectKeys() {
    method addComment (line 80) | public void addComment(String issueId, String comment, String groupVis...
    method addLabels (line 91) | public void addLabels(String issueId, List<String> labels) {
    method addFields (line 116) | public void addFields(String issueId, List<JiraIssueField> fields) {
    method getIssue (line 126) | public Issue getIssue(String id) {
    method getIssuesFromJqlSearch (line 136) | public List<Issue> getIssuesFromJqlSearch(final String jqlSearch) thro...
    method getVersions (line 146) | public List<ExtendedVersion> getVersions(String projectKey) {
    method getVersionByName (line 158) | public ExtendedVersion getVersionByName(String projectKey, String name) {
    method getIssuesWithFixVersion (line 172) | public List<Issue> getIssuesWithFixVersion(String projectKey, String v...
    method getIssuesWithFixVersion (line 176) | public List<Issue> getIssuesWithFixVersion(String projectKey, String v...
    method getIssueTypes (line 193) | public List<IssueType> getIssueTypes() {
    method getPriorities (line 203) | public List<Priority> getPriorities() {
    method releaseVersion (line 211) | public void releaseVersion(String projectKey, ExtendedVersion version) {
    method migrateIssuesToFixVersion (line 223) | public void migrateIssuesToFixVersion(String projectKey, String versio...
    method replaceFixVersion (line 252) | public void replaceFixVersion(String projectKey, String fromVersion, S...
    method addFixVersion (line 309) | public void addFixVersion(String projectKey, String version, String qu...
    method progressWorkflowAction (line 343) | public String progressWorkflowAction(String issueKey, Integer actionId) {
    method getActionIdForIssue (line 355) | public Integer getActionIdForIssue(String issueKey, String workflowAct...
    method getStatusById (line 374) | public String getStatusById(Long statusId) {
    method getKnownStatuses (line 394) | private Map<Long, String> getKnownStatuses() {
    method createIssue (line 410) | @Deprecated
    method createIssue (line 416) | public Issue createIssue(
    method addCommentWithoutConstrains (line 432) | public void addCommentWithoutConstrains(String issueId, String comment) {
    method getIssueByKey (line 441) | public Issue getIssueByKey(String issueId) {
    method getComponents (line 450) | public List<Component> getComponents(String projectKey) {
    method addVersion (line 461) | public Version addVersion(String version, String projectKey) {
    method getMyPermissions (line 468) | public Permissions getMyPermissions() {

FILE: src/main/java/hudson/plugins/jira/JiraSessionFactory.java
  class JiraSessionFactory (line 15) | public class JiraSessionFactory {
    method create (line 28) | public static JiraSession create(JiraSite jiraSite, URI uri, StandardU...

FILE: src/main/java/hudson/plugins/jira/JiraSite.java
  class JiraSite (line 94) | public class JiraSite extends AbstractDescribableImpl<JiraSite> {
    method JiraSite (line 276) | @Deprecated
    method JiraSite (line 305) | @Deprecated
    method JiraSite (line 333) | @Deprecated
    method JiraSite (line 373) | @Deprecated
    method JiraSite (line 412) | @DataBoundConstructor
    method JiraSite (line 422) | @Deprecated
    method JiraSite (line 454) | @Deprecated
    method toURL (line 487) | static URL toURL(String url) {
    method setDisableChangelogAnnotations (line 502) | @DataBoundSetter
    method getDisableChangelogAnnotations (line 507) | public boolean getDisableChangelogAnnotations() {
    method setTimeout (line 517) | @DataBoundSetter
    method getTimeout (line 522) | public int getTimeout() {
    method setReadTimeout (line 532) | @DataBoundSetter
    method getReadTimeout (line 537) | public int getReadTimeout() {
    method getCredentialsId (line 541) | public String getCredentialsId() {
    method setCredentialsId (line 545) | @DataBoundSetter
    method setDateTimePattern (line 550) | @DataBoundSetter
    method setThreadExecutorNumber (line 555) | @DataBoundSetter
    method getThreadExecutorNumber (line 560) | public int getThreadExecutorNumber() {
    method setAppendChangeTimestamp (line 564) | @DataBoundSetter
    method getDateTimePattern (line 569) | public String getDateTimePattern() {
    method isAppendChangeTimestamp (line 573) | public boolean isAppendChangeTimestamp() {
    method getAlternativeUrl (line 577) | public URL getAlternativeUrl() {
    method isUseHTTPAuth (line 581) | public boolean isUseHTTPAuth() {
    method isUseBearerAuth (line 585) | public boolean isUseBearerAuth() {
    method getGroupVisibility (line 589) | public String getGroupVisibility() {
    method getRoleVisibility (line 593) | public String getRoleVisibility() {
    method isSupportsWikiStyleComment (line 597) | public boolean isSupportsWikiStyleComment() {
    method isRecordScmChanges (line 601) | public boolean isRecordScmChanges() {
    method isUpdateJiraIssueForAllStatus (line 605) | public boolean isUpdateJiraIssueForAllStatus() {
    method setAlternativeUrl (line 609) | @DataBoundSetter
    method setUseHTTPAuth (line 614) | @DataBoundSetter
    method setUseBearerAuth (line 619) | @DataBoundSetter
    method setGroupVisibility (line 624) | @DataBoundSetter
    method setRoleVisibility (line 629) | @DataBoundSetter
    method setSupportsWikiStyleComment (line 634) | @DataBoundSetter
    method setRecordScmChanges (line 639) | @DataBoundSetter
    method setUserPattern (line 644) | @DataBoundSetter
    method setUpdateJiraIssueForAllStatus (line 655) | @DataBoundSetter
    method setMaxIssuesFromJqlSearch (line 660) | @DataBoundSetter
    method getMaxIssuesFromJqlSearch (line 667) | public int getMaxIssuesFromJqlSearch() {
    method readResolve (line 671) | @SuppressWarnings("unused")
    method makeIssueCache (line 716) | protected static Cache<String, Optional<Issue>> makeIssueCache() {
    method getName (line 720) | public String getName() {
    method getSession (line 727) | @Deprecated
    method getSession (line 738) | @Nullable
    method getSession (line 743) | JiraSession getSession(Item item, boolean uiValidation) {
    method createSession (line 750) | JiraSession createSession(Item item) {
    method createSession (line 759) | JiraSession createSession(Item item, boolean uiValidation) {
    method getProjectUpdateLock (line 782) | Lock getProjectUpdateLock() {
    method resolveCredentials (line 793) | private StandardUsernamePasswordCredentials resolveCredentials(Item it...
    method getHttpClientOptions (line 822) | protected HttpClientOptions getHttpClientOptions() {
    method getExecutorService (line 831) | private ExecutorService getExecutorService() {
    method destroy (line 854) | @PreDestroy
    class ExtendedAsynchronousJiraRestClientFactory (line 867) | public static class ExtendedAsynchronousJiraRestClientFactory implemen...
      method create (line 869) | public ExtendedJiraRestClient create(
      method create (line 882) | @Override
      method createWithBasicHttpAuthentication (line 889) | @Override
      method createWithAuthenticationHandler (line 895) | @Override
      method create (line 901) | @Override
    method createClient (line 908) | private static DisposableHttpClient createClient(
    method createClient (line 937) | private static DisposableHttpClient createClient(final HttpClient clie...
    class NoOpEventPublisher (line 950) | private static class NoOpEventPublisher implements EventPublisher {
      method publish (line 951) | @Override
      method register (line 954) | @Override
      method unregister (line 957) | @Override
      method unregisterAll (line 960) | @Override
    class RestClientApplicationProperties (line 964) | @SuppressWarnings("deprecation")
      method RestClientApplicationProperties (line 969) | private RestClientApplicationProperties(URI jiraURI) {
      method getBaseUrl (line 973) | @Override
      method getBaseUrl (line 981) | @NonNull
      method getDisplayName (line 987) | @NonNull
      method getPlatformId (line 993) | @NonNull
      method getVersion (line 999) | @NonNull
      method getBuildDate (line 1005) | @NonNull
      method getBuildNumber (line 1011) | @NonNull
      method getHomeDirectory (line 1017) | @Override
      method getPropertyValue (line 1022) | @Override
      method getApplicationFileEncoding (line 1027) | @NonNull
      method getLocalHomeDirectory (line 1033) | @NonNull
      method getSharedHomeDirectory (line 1039) | @NonNull
    method getUrl (line 1053) | @Nullable
    method getUrl (line 1061) | public URL getUrl(JiraIssue issue) throws IOException {
    method getUrl (line 1068) | public URL getUrl(String id) throws MalformedURLException {
    method getAlternativeUrl (line 1075) | public URL getAlternativeUrl(String id) throws MalformedURLException {
    method getUserPattern (line 1084) | public Pattern getUserPattern() {
    method getIssuePattern (line 1098) | public Pattern getIssuePattern() {
    method getProjectKeys (line 1107) | public Set<String> getProjectKeys(Item item) {
    method getIssue (line 1138) | @CheckForNull
    method existsIssue (line 1153) | @Deprecated
    method getVersions (line 1169) | @Deprecated
    method getReleaseNotesForFixVersion (line 1187) | public String getReleaseNotesForFixVersion(String projectKey, String v...
    method replaceFixVersion (line 1239) | public void replaceFixVersion(String projectKey, String fromVersion, S...
    method migrateIssuesToFixVersion (line 1256) | public void migrateIssuesToFixVersion(String projectKey, String versio...
    method addFixVersionToIssue (line 1272) | public void addFixVersionToIssue(String projectKey, String versionName...
    method progressMatchingIssues (line 1290) | public boolean progressMatchingIssues(
    class DescriptorImpl (line 1340) | @Extension
      method getDisplayName (line 1342) | @Override
      method doCheckUrl (line 1347) | @SuppressWarnings("unused") // used by stapler
      method doCheckAlternativeUrl (line 1352) | @SuppressWarnings("unused") // used by stapler
      method checkUrl (line 1357) | private FormValidation checkUrl(String url) {
      method doValidate (line 1372) | @RequirePOST
      method doFillCredentialsIdItems (line 1455) | @SuppressWarnings("unused") // Used by stapler
      method doCheckCredentialsId (line 1463) | @SuppressWarnings("unused") // Used by stapler
      method getBuilder (line 1469) | Builder getBuilder() {
    class Builder (line 1474) | static class Builder {
      method withMainURL (line 1486) | public Builder withMainURL(URL mainURL) {
      method withAlternativeURL (line 1491) | public Builder withAlternativeURL(URL alternativeURL) {
      method withCredentialsId (line 1496) | public Builder withCredentialsId(String credentialsId) {
      method withSupportsWikiStyleComment (line 1501) | public Builder withSupportsWikiStyleComment(boolean supportsWikiStyl...
      method withRecordScmChanges (line 1506) | public Builder withRecordScmChanges(boolean recordScmChanges) {
      method withUserPattern (line 1511) | public Builder withUserPattern(String userPattern) {
      method withUpdateJiraIssueForAllStatus (line 1516) | public Builder withUpdateJiraIssueForAllStatus(boolean updateJiraIss...
      method withGroupVisibility (line 1521) | public Builder withGroupVisibility(String groupVisibility) {
      method withRoleVisibility (line 1526) | public Builder withRoleVisibility(String roleVisibility) {
      method withUseHTTPAuth (line 1531) | public Builder withUseHTTPAuth(boolean useHTTPAuth) {
      method build (line 1536) | public JiraSite build() {
    method map (line 1558) | public static ItemGroup map(Item item) {
    method getJiraSites (line 1569) | public static List<JiraSite> getJiraSites(Item item) {
    method getSitesFromFolders (line 1581) | public static List<JiraSite> getSitesFromFolders(ItemGroup itemGroup) {
    method get (line 1603) | @Nullable

FILE: src/main/java/hudson/plugins/jira/JiraVersionCreator.java
  class JiraVersionCreator (line 24) | @Deprecated
    method JiraVersionCreator (line 31) | @DataBoundConstructor
    method getRequiredMonitorService (line 37) | @Override
    method getJiraVersion (line 42) | public String getJiraVersion() {
    method setJiraVersion (line 46) | public void setJiraVersion(String jiraVersion) {
    method getJiraProjectKey (line 50) | public String getJiraProjectKey() {
    method setJiraProjectKey (line 54) | public void setJiraProjectKey(String jiraProjectKey) {
    method isFailIfAlreadyExists (line 58) | public boolean isFailIfAlreadyExists() {
    method setFailIfAlreadyExists (line 62) | @DataBoundSetter
    method perform (line 67) | @Override
    method getDescriptor (line 76) | @Override
    method readResolve (line 81) | protected Object readResolve() {
    class DescriptorImpl (line 92) | public static class DescriptorImpl extends BuildStepDescriptor<Publish...
      method DescriptorImpl (line 94) | public DescriptorImpl() {
      method isApplicable (line 98) | @Override
      method newInstance (line 103) | @Override
      method getDisplayName (line 108) | @Override
      method getHelpFile (line 113) | @Override

FILE: src/main/java/hudson/plugins/jira/JiraVersionCreatorBuilder.java
  class JiraVersionCreatorBuilder (line 25) | public class JiraVersionCreatorBuilder extends Builder implements Simple...
    method JiraVersionCreatorBuilder (line 31) | @DataBoundConstructor
    method getRequiredMonitorService (line 37) | @Override
    method getJiraVersion (line 42) | public String getJiraVersion() {
    method setJiraVersion (line 46) | public void setJiraVersion(String jiraVersion) {
    method getJiraProjectKey (line 50) | public String getJiraProjectKey() {
    method setJiraProjectKey (line 54) | public void setJiraProjectKey(String jiraProjectKey) {
    method isFailIfAlreadyExists (line 58) | public boolean isFailIfAlreadyExists() {
    method readResolve (line 62) | protected Object readResolve() {
    method setFailIfAlreadyExists (line 70) | @DataBoundSetter
    method perform (line 75) | @Override
    method requiresWorkspace (line 84) | @Override
    method getDescriptor (line 89) | @Override
    class DescriptorImpl (line 97) | @Symbol("jiraCreateVersion")
      method DescriptorImpl (line 100) | public DescriptorImpl() {
      method isApplicable (line 104) | @Override
      method newInstance (line 109) | @Override
      method getDisplayName (line 114) | @Override
      method getHelpFile (line 119) | @Override

FILE: src/main/java/hudson/plugins/jira/RunScmChangeExtractor.java
  class RunScmChangeExtractor (line 16) | public class RunScmChangeExtractor {
    method RunScmChangeExtractor (line 22) | private RunScmChangeExtractor() {}
    method getChanges (line 24) | public static List<ChangeLogSet<? extends Entry>> getChanges(Run<?, ?>...
    method getChangesUsingReflection (line 47) | @SuppressWarnings("unchecked")
    method getDependencyChanges (line 74) | public static Map<AbstractProject, DependencyChange> getDependencyChan...

FILE: src/main/java/hudson/plugins/jira/Updater.java
  class Updater (line 43) | class Updater {
    method Updater (line 55) | Updater(SCM scm) {
    method Updater (line 59) | Updater(SCM scm, List<String> labels) {
    method perform (line 68) | boolean perform(Run<?, ?> run, TaskListener listener, AbstractIssueSel...
    method submitComments (line 155) | void submitComments(
    method getJiraIssues (line 210) | private static Set<JiraIssue> getJiraIssues(Set<String> ids, JiraSessi...
    method createComment (line 234) | private String createComment(
    method getScmComments (line 261) | private String getScmComments(boolean wikiStyle, Run<?, ?> run, boolea...
    method createScmChangeEntryDescription (line 285) | protected String createScmChangeEntryDescription(
    method appendAuthorToDescription (line 312) | protected void appendAuthorToDescription(Entry change, StringBuilder d...
    method appendRevisionToDescription (line 322) | protected void appendRevisionToDescription(
    method appendAffectedFilesToDescription (line 348) | protected void appendAffectedFilesToDescription(Entry change, StringBu...
    method appendChangeTimestampToDescription (line 374) | protected void appendChangeTimestampToDescription(StringBuilder descri...
    method getRepositoryBrowser (line 387) | private RepositoryBrowser<?> getRepositoryBrowser(Run<?, ?> run) {
    method getRevision (line 395) | private static String getRevision(Entry entry) {
    method getScm (line 413) | private SCM getScm() {

FILE: src/main/java/hudson/plugins/jira/VersionCreator.java
  class VersionCreator (line 19) | class VersionCreator {
    method setFailIfAlreadyExists (line 29) | public VersionCreator setFailIfAlreadyExists(boolean failIfAlreadyExis...
    method setJiraVersion (line 34) | public VersionCreator setJiraVersion(String jiraVersion) {
    method setJiraProjectKey (line 39) | public VersionCreator setJiraProjectKey(String jiraProjectKey) {
    method perform (line 44) | protected boolean perform(Job<?, ?> project, Run<?, ?> build, TaskList...
    method addVersion (line 95) | protected void addVersion(String version, String projectKey, JiraSessi...
    method getSiteForProject (line 104) | protected JiraSite getSiteForProject(Job<?, ?> project) {

FILE: src/main/java/hudson/plugins/jira/VersionReleaser.java
  class VersionReleaser (line 18) | public class VersionReleaser {
    method perform (line 22) | protected boolean perform(
    method releaseVersion (line 75) | protected void releaseVersion(
    method getSiteForProject (line 102) | protected JiraSite getSiteForProject(Job<?, ?> project) {

FILE: src/main/java/hudson/plugins/jira/auth/BearerHttpAuthenticationHandler.java
  class BearerHttpAuthenticationHandler (line 11) | public class BearerHttpAuthenticationHandler implements AuthenticationHa...
    method BearerHttpAuthenticationHandler (line 20) | public BearerHttpAuthenticationHandler(final String token) {
    method configure (line 24) | @Override

FILE: src/main/java/hudson/plugins/jira/extension/ExtendedAsynchronousJiraRestClient.java
  class ExtendedAsynchronousJiraRestClient (line 8) | public class ExtendedAsynchronousJiraRestClient extends AsynchronousJira...
    method ExtendedAsynchronousJiraRestClient (line 12) | public ExtendedAsynchronousJiraRestClient(URI serverUri, DisposableHtt...
    method getExtendedVersionRestClient (line 20) | @Override
    method getExtendedMyPermissionsRestClient (line 25) | @Override

FILE: src/main/java/hudson/plugins/jira/extension/ExtendedAsynchronousMyPermissionsRestClient.java
  class ExtendedAsynchronousMyPermissionsRestClient (line 11) | public class ExtendedAsynchronousMyPermissionsRestClient extends Asynchr...
    method ExtendedAsynchronousMyPermissionsRestClient (line 18) | ExtendedAsynchronousMyPermissionsRestClient(final URI baseUri, final H...
    method getMyPermissions (line 23) | @Override

FILE: src/main/java/hudson/plugins/jira/extension/ExtendedAsynchronousVersionRestClient.java
  class ExtendedAsynchronousVersionRestClient (line 9) | public class ExtendedAsynchronousVersionRestClient extends AsynchronousV...
    method ExtendedAsynchronousVersionRestClient (line 13) | ExtendedAsynchronousVersionRestClient(URI baseUri, HttpClient client) {
    method getExtendedVersion (line 18) | @Override
    method createExtendedVersion (line 23) | @Override
    method updateExtendedVersion (line 29) | @Override

FILE: src/main/java/hudson/plugins/jira/extension/ExtendedJiraRestClient.java
  type ExtendedJiraRestClient (line 5) | public interface ExtendedJiraRestClient extends JiraRestClient {
    method getExtendedVersionRestClient (line 6) | ExtendedVersionRestClient getExtendedVersionRestClient();
    method getExtendedMyPermissionsRestClient (line 8) | ExtendedMyPermissionsRestClient getExtendedMyPermissionsRestClient();

FILE: src/main/java/hudson/plugins/jira/extension/ExtendedMyPermissionsRestClient.java
  type ExtendedMyPermissionsRestClient (line 6) | public interface ExtendedMyPermissionsRestClient {
    method getMyPermissions (line 8) | Promise<Permissions> getMyPermissions();

FILE: src/main/java/hudson/plugins/jira/extension/ExtendedVersion.java
  class ExtendedVersion (line 8) | public class ExtendedVersion extends Version {
    method ExtendedVersion (line 11) | public ExtendedVersion(
    method getStartDate (line 24) | @Nullable

FILE: src/main/java/hudson/plugins/jira/extension/ExtendedVersionInput.java
  class ExtendedVersionInput (line 9) | public class ExtendedVersionInput extends VersionInput {
    method ExtendedVersionInput (line 12) | public ExtendedVersionInput(
    method toString (line 24) | @Override
    method equals (line 32) | @Override
    method hashCode (line 41) | @Override
    method getStartDate (line 46) | DateTime getStartDate() {

FILE: src/main/java/hudson/plugins/jira/extension/ExtendedVersionInputJsonGenerator.java
  class ExtendedVersionInputJsonGenerator (line 8) | public class ExtendedVersionInputJsonGenerator implements JsonGenerator<...
    method generate (line 9) | @Override

FILE: src/main/java/hudson/plugins/jira/extension/ExtendedVersionJsonParser.java
  class ExtendedVersionJsonParser (line 10) | public class ExtendedVersionJsonParser implements JsonObjectParser<Exten...
    method parse (line 11) | @Override
    method parseDate (line 26) | private DateTime parseDate(String dateStr) {

FILE: src/main/java/hudson/plugins/jira/extension/ExtendedVersionRestClient.java
  type ExtendedVersionRestClient (line 7) | public interface ExtendedVersionRestClient extends VersionRestClient {
    method getExtendedVersion (line 8) | Promise<ExtendedVersion> getExtendedVersion(URI versionUri);
    method createExtendedVersion (line 10) | Promise<ExtendedVersion> createExtendedVersion(ExtendedVersionInput ve...
    method updateExtendedVersion (line 12) | Promise<ExtendedVersion> updateExtendedVersion(URI versionUri, Extende...

FILE: src/main/java/hudson/plugins/jira/listissuesparameter/JiraIssueParameterDefinition.java
  class JiraIssueParameterDefinition (line 50) | public class JiraIssueParameterDefinition extends ParameterDefinition {
    method JiraIssueParameterDefinition (line 56) | @DataBoundConstructor
    method createValue (line 62) | @Override
    method createValue (line 72) | @Override
    method createValue (line 78) | @Override
    method getIssues (line 83) | public List<JiraIssueParameterDefinition.Result> getIssues()
    method getIssues (line 89) | List<JiraIssueParameterDefinition.Result> getIssues(Job<?, ?> job) {
    method getJiraIssueFilter (line 112) | public String getJiraIssueFilter() {
    method setJiraIssueFilter (line 116) | public void setJiraIssueFilter(String jiraIssueFilter) {
    method getAltSummaryFields (line 120) | public String getAltSummaryFields() {
    method setAltSummaryFields (line 124) | @DataBoundSetter
    class DescriptorImpl (line 129) | @Extension
      method getDisplayName (line 132) | @Override
      method doFillValueItems (line 137) | @RequirePOST
    class Result (line 157) | public static class Result {
      method Result (line 161) | public Result(final Issue issue) {
      method Result (line 165) | public Result(final Issue issue, String altSummaryFields) {

FILE: src/main/java/hudson/plugins/jira/listissuesparameter/JiraIssueParameterValue.java
  class JiraIssueParameterValue (line 27) | public class JiraIssueParameterValue extends ParameterValue {
    method JiraIssueParameterValue (line 32) | @DataBoundConstructor
    method buildEnvironment (line 38) | @Override
    method createVariableResolver (line 44) | @Override
    method setValue (line 58) | public void setValue(final String value) {
    method getValue (line 62) | @Override
    method toString (line 68) | @Override

FILE: src/main/java/hudson/plugins/jira/model/JiraIssue.java
  class JiraIssue (line 17) | @ExportedBean
    method JiraIssue (line 25) | public JiraIssue(String key, String summary) {
    method getKey (line 33) | @Exported
    method getSummary (line 41) | @Exported
    method JiraIssue (line 46) | public JiraIssue(Issue issue) {
    method compareTo (line 50) | @Override
    method hashCode (line 55) | @Override
    method equals (line 63) | @Override

FILE: src/main/java/hudson/plugins/jira/model/JiraIssueField.java
  class JiraIssueField (line 3) | public class JiraIssueField implements Comparable<JiraIssueField> {
    method JiraIssueField (line 8) | public JiraIssueField(String fieldId, Object fieldValue) {
    method compareTo (line 13) | @Override
    method hashCode (line 18) | @Override
    method equals (line 27) | @Override
    method getId (line 59) | public String getId() {
    method getValue (line 63) | public Object getValue() {

FILE: src/main/java/hudson/plugins/jira/model/JiraVersion.java
  class JiraVersion (line 7) | public class JiraVersion implements Comparable<JiraVersion> {
    method JiraVersion (line 16) | public JiraVersion(String name, Calendar releaseDate, boolean released...
    method JiraVersion (line 23) | @Deprecated
    method JiraVersion (line 32) | public JiraVersion(
    method JiraVersion (line 47) | public JiraVersion(Version version) {
    method JiraVersion (line 57) | public JiraVersion(ExtendedVersion version) {
    method compareTo (line 69) | @Override
    method hashCode (line 78) | @Override
    method equals (line 89) | @Override
    method getName (line 131) | public String getName() {
    method getDescription (line 135) | public String getDescription() {
    method getStartDate (line 139) | public Calendar getStartDate() {
    method getReleaseDate (line 143) | public Calendar getReleaseDate() {
    method isReleased (line 147) | public boolean isReleased() {
    method isArchived (line 151) | public boolean isArchived() {

FILE: src/main/java/hudson/plugins/jira/pipeline/CommentStep.java
  class CommentStep (line 26) | public class CommentStep extends Step {
    method CommentStep (line 32) | @DataBoundConstructor
    method getIssueKey (line 38) | public String getIssueKey() {
    method getBody (line 42) | public String getBody() {
    method start (line 46) | @Override
    class DescriptorImpl (line 51) | @Extension(optional = true)
      method getRequiredContext (line 54) | @Override
      method getFunctionName (line 61) | @Override
      method getDisplayName (line 66) | @Override
    class CommentStepExecution (line 75) | public static class CommentStepExecution extends SynchronousNonBlockin...
      method CommentStepExecution (line 81) | protected CommentStepExecution(CommentStep step, @NonNull StepContex...
      method run (line 86) | @Override

FILE: src/main/java/hudson/plugins/jira/pipeline/IssueFieldUpdateStep.java
  class IssueFieldUpdateStep (line 38) | public class IssueFieldUpdateStep extends Builder implements SimpleBuild...
    method getIssueSelector (line 42) | public AbstractIssueSelector getIssueSelector() {
    method setIssueSelector (line 46) | @DataBoundSetter
    method getFieldId (line 53) | public String getFieldId() {
    method setFieldId (line 57) | @DataBoundSetter
    method getFieldValue (line 64) | public String getFieldValue() {
    method setFieldValue (line 68) | @DataBoundSetter
    method IssueFieldUpdateStep (line 73) | @DataBoundConstructor
    method prepareFieldId (line 80) | public String prepareFieldId(String fieldId) {
    method perform (line 88) | @Override
    method requiresWorkspace (line 137) | @Override
    method submitFields (line 145) | @Deprecated
    method getDescriptor (line 169) | @Override
    class DescriptorImpl (line 174) | @Extension
      method doCheckField_id (line 178) | public FormValidation doCheckField_id(@QueryParameter String value) ...
      method isApplicable (line 188) | @Override
      method getDisplayName (line 193) | @Override

FILE: src/main/java/hudson/plugins/jira/pipeline/IssueSelectorStep.java
  class IssueSelectorStep (line 32) | public class IssueSelectorStep extends Step {
    method IssueSelectorStep (line 36) | @DataBoundConstructor
    method setIssueSelector (line 39) | @DataBoundSetter
    method getIssueSelector (line 44) | public AbstractIssueSelector getIssueSelector() {
    method start (line 48) | @Override
    class DescriptorImpl (line 53) | @Extension(optional = true)
      method getApplicableDescriptors (line 56) | public Collection<? extends Descriptor<?>> getApplicableDescriptors() {
      method getRequiredContext (line 60) | @Override
      method getFunctionName (line 67) | @Override
      method getDisplayName (line 72) | @Override
    class IssueSelectorStepExecution (line 78) | public static class IssueSelectorStepExecution extends SynchronousNonB...
      method IssueSelectorStepExecution (line 84) | protected IssueSelectorStepExecution(IssueSelectorStep step, @NonNul...
      method run (line 89) | @Override

FILE: src/main/java/hudson/plugins/jira/pipeline/SearchIssuesStep.java
  class SearchIssuesStep (line 30) | public class SearchIssuesStep extends Step {
    method SearchIssuesStep (line 34) | @DataBoundConstructor
    method getJql (line 39) | public String getJql() {
    method start (line 43) | @Override
    class DescriptorImpl (line 48) | @Extension(optional = true)
      method getRequiredContext (line 51) | @Override
      method getFunctionName (line 58) | @Override
      method getDisplayName (line 63) | @Override
    class SearchStepExecution (line 72) | public static class SearchStepExecution extends SynchronousNonBlocking...
      method SearchStepExecution (line 78) | protected SearchStepExecution(SearchIssuesStep step, @NonNull StepCo...
      method run (line 83) | @Override

FILE: src/main/java/hudson/plugins/jira/selector/AbstractIssueSelector.java
  class AbstractIssueSelector (line 16) | public abstract class AbstractIssueSelector extends AbstractDescribableI...
    method findIssueIds (line 30) | public abstract Set<String> findIssueIds(

FILE: src/main/java/hudson/plugins/jira/selector/DefaultIssueSelector.java
  class DefaultIssueSelector (line 31) | public class DefaultIssueSelector extends AbstractIssueSelector {
    method DefaultIssueSelector (line 35) | @DataBoundConstructor
    method findIssueIds (line 41) | @Override
    class DescriptorImpl (line 49) | @Extension
      method getDisplayName (line 53) | @Override
    method getLogger (line 59) | protected Logger getLogger() {
    method findIssues (line 70) | protected static void findIssues(Run<?, ?> build, Set<String> issueIds...
    method addIssuesFromChangeLog (line 93) | protected void addIssuesFromChangeLog(Run<?, ?> build, JiraSite site, ...
    method addIssuesRecursive (line 105) | protected void addIssuesRecursive(Run<?, ?> build, JiraSite site, Task...
    method addIssuesFromCurrentBuild (line 117) | protected void addIssuesFromCurrentBuild(
    method addIssuesFromDependentBuilds (line 128) | protected void addIssuesFromDependentBuilds(
    method addIssuesFromParameters (line 147) | protected void addIssuesFromParameters(
    method addIssuesCarriedOverFromPreviousBuild (line 168) | protected void addIssuesCarriedOverFromPreviousBuild(

FILE: src/main/java/hudson/plugins/jira/selector/ExplicitIssueSelector.java
  class ExplicitIssueSelector (line 22) | public class ExplicitIssueSelector extends AbstractIssueSelector {
    method ExplicitIssueSelector (line 29) | @DataBoundConstructor
    method ExplicitIssueSelector (line 36) | public ExplicitIssueSelector(List<String> jiraIssueKeys) {
    method ExplicitIssueSelector (line 40) | public ExplicitIssueSelector() {
    method setIssueKeys (line 44) | public void setIssueKeys(String issueKeys) {
    method getIssueKeys (line 50) | public String getIssueKeys() {
    method findIssueIds (line 54) | @Override
    class DescriptorImpl (line 66) | @Extension
      method getDisplayName (line 69) | @Override

FILE: src/main/java/hudson/plugins/jira/selector/JqlIssueSelector.java
  class JqlIssueSelector (line 22) | public class JqlIssueSelector extends AbstractIssueSelector {
    method JqlIssueSelector (line 26) | @DataBoundConstructor
    method setJql (line 31) | public void setJql(String jql) {
    method getJql (line 35) | public String getJql() {
    method findIssueIds (line 39) | @Override
    class DescriptorImpl (line 64) | @Extension
      method getDisplayName (line 68) | @Override

FILE: src/main/java/hudson/plugins/jira/selector/perforce/JobIssueSelector.java
  class JobIssueSelector (line 17) | public abstract class JobIssueSelector extends DefaultIssueSelector {
    method addIssuesFromChangeLog (line 22) | @Override
    method addJobIdsFromChangeLog (line 30) | protected abstract void addJobIdsFromChangeLog(

FILE: src/main/java/hudson/plugins/jira/selector/perforce/P4JobIssueSelector.java
  class P4JobIssueSelector (line 27) | public class P4JobIssueSelector extends JobIssueSelector {
    class DescriptorImpl (line 30) | @Extension(optional = true)
      method getDisplayName (line 34) | @Override
    method P4JobIssueSelector (line 40) | @DataBoundConstructor
    method addJobIdsFromChangeLog (line 43) | @Override
    method getLogger (line 66) | @Override

FILE: src/main/java/hudson/plugins/jira/versionparameter/JiraVersionParameterDefinition.java
  class JiraVersionParameterDefinition (line 30) | public class JiraVersionParameterDefinition extends ParameterDefinition {
    method JiraVersionParameterDefinition (line 39) | @DataBoundConstructor
    method createValue (line 57) | @Override
    method createValue (line 66) | @Override
    method createValue (line 72) | @Override
    method getVersions (line 77) | public List<JiraVersionParameterDefinition.Result> getVersions() throw...
    method getVersions (line 82) | List<JiraVersionParameterDefinition.Result> getVersions(Job<?, ?> cont...
    method match (line 101) | private boolean match(Version version) {
    method getJiraReleasePattern (line 132) | public String getJiraReleasePattern() {
    method setJiraReleasePattern (line 139) | public void setJiraReleasePattern(String pattern) {
    method getJiraProjectKey (line 147) | public String getJiraProjectKey() {
    method setJiraProjectKey (line 151) | public void setJiraProjectKey(String projectKey) {
    method getJiraShowReleased (line 155) | public String getJiraShowReleased() {
    method setJiraShowReleased (line 159) | public void setJiraShowReleased(String showReleased) {
    method getJiraShowArchived (line 163) | public String getJiraShowArchived() {
    method setJiraShowArchived (line 167) | public void setJiraShowArchived(String showArchived) {
    method getJiraShowUnreleased (line 171) | public String getJiraShowUnreleased() {
    method setShowUnreleased (line 175) | public void setShowUnreleased(String jiraShowUnreleased) {
    class DescriptorImpl (line 179) | @Extension
      method getDisplayName (line 182) | @Override
      method doFillVersionItems (line 187) | @RequirePOST
    class Result (line 207) | public static class Result {
      method Result (line 211) | public Result(final Version version) {
      method equals (line 216) | @Override
      method hashCode (line 223) | @Override

FILE: src/main/java/hudson/plugins/jira/versionparameter/JiraVersionParameterValue.java
  class JiraVersionParameterValue (line 10) | public class JiraVersionParameterValue extends ParameterValue {
    method JiraVersionParameterValue (line 19) | @DataBoundConstructor
    method buildEnvironment (line 28) | @Override
    method createVariableResolver (line 33) | @Override
    method setVersion (line 38) | public void setVersion(final String version) {
    method getVersion (line 42) | public String getVersion() {
    method getValue (line 46) | @Override
    method toString (line 51) | @Override

FILE: src/main/java/hudson/plugins/jira/versionparameter/VersionComparator.java
  class VersionComparator (line 18) | public class VersionComparator implements Comparator<Version> {
    method compare (line 22) | @Override

FILE: src/test/java/JiraConfig.java
  class JiraConfig (line 3) | public final class JiraConfig {
    method getUrl (line 7) | public static String getUrl() {
    method getUsername (line 11) | public static String getUsername() {
    method getPassword (line 15) | public static String getPassword() {
    method getToken (line 19) | public static String getToken() {

FILE: src/test/java/JiraTester.java
  class JiraTester (line 21) | public class JiraTester {
    method main (line 22) | public static void main(String[] args) throws Exception {
    method callUniq (line 102) | private static void callUniq(final JiraRestService restService) throws...
    method callDuplicate (line 110) | private static void callDuplicate(final JiraRestService restService) t...

FILE: src/test/java/JiraTesterBearerAuth.java
  class JiraTesterBearerAuth (line 22) | public class JiraTesterBearerAuth {
    method main (line 23) | public static void main(String[] args) throws Exception {
    method callUniq (line 104) | private static void callUniq(final JiraRestService restService) throws...
    method callDuplicate (line 111) | private static void callDuplicate(final JiraRestService restService) t...

FILE: src/test/java/com/atlassian/httpclient/apache/httpcomponents/ApacheAsyncHttpClientTest.java
  class ApacheAsyncHttpClientTest (line 38) | @WithJenkins
    method prepare (line 49) | public void prepare(Handler handler) throws Exception {
    method dispose (line 57) | @AfterEach
    method simple_get (line 64) | @Test
    method simple_post (line 80) | @Test
    method simple_get_with_non_proxy_host (line 99) | @Test
    method simple_get_with_proxy (line 115) | @Test
    method simple_post_with_proxy (line 130) | @Test
    class ProxyTestHandler (line 152) | public static class ProxyTestHandler extends Handler.Abstract {
      method handle (line 164) | @Override
    class TestHandler (line 196) | public static class TestHandler extends Handler.Abstract {
      method handle (line 200) | @Override
    method buildApplicationProperties (line 212) | private ApplicationProperties buildApplicationProperties() {
    class NoOpThreadLocalContextManager (line 287) | private static final class NoOpThreadLocalContextManager<C> implements...
      method getThreadLocalContext (line 288) | @Override
      method setThreadLocalContext (line 293) | @Override
      method clearThreadLocalContext (line 296) | @Override

FILE: src/test/java/com/atlassian/httpclient/apache/httpcomponents/CompletableFuturePromiseHttpPromiseAsyncClientTest.java
  class CompletableFuturePromiseHttpPromiseAsyncClientTest (line 25) | @ExtendWith(MockitoExtension.class)
    method ensureCloseHttpclientOnCompletion (line 49) | @Test
    method ensureCloseHttpclientOnFailure (line 61) | @Test
    method ensureCloseHttpclientOnCancellation (line 73) | @Test

FILE: src/test/java/hudson/plugins/jira/BuildListenerResultMethodMock.java
  class BuildListenerResultMethodMock (line 7) | public class BuildListenerResultMethodMock implements Answer<Void> {
    method answer (line 11) | @Override
    method getResult (line 17) | public Result getResult() {

FILE: src/test/java/hudson/plugins/jira/ChangingWorkflowTest.java
  class ChangingWorkflowTest (line 39) | @ExtendWith(MockitoExtension.class)
    method setupSpy (line 60) | @BeforeEach
    method onGetActionItInvokesServiceMethod (line 65) | @Test
    method getActionIdReturnsNullWhenServiceReturnsNull (line 71) | @Test
    method getActionIdIteratesOverAllActionsEvenOneOfNamesIsNull (line 77) | @Test
    method getActionIdReturnsNullWhenNullWorkflowUsed (line 92) | @Test
    method getActionIdReturnsIdWhenFoundIgnorecaseWorkflow (line 102) | @Test
    method addCommentsOnNonEmptyWorkflowAndNonEmptyComment (line 114) | @Test
    method addCommentsOnNullWorkflowAndNonEmptyComment (line 132) | @Test
    method dontAddCommentsOnNullWorkflowAndNullComment (line 148) | @Test

FILE: src/test/java/hudson/plugins/jira/CliParameterTest.java
  class CliParameterTest (line 18) | @WithJenkins
    method setup (line 25) | @BeforeEach
    method jiraIssueParameterViaCli (line 31) | @Test
    method jiraVersionParameterViaCli (line 41) | @Test

FILE: src/test/java/hudson/plugins/jira/ConfigAsCodeTest.java
  class ConfigAsCodeTest (line 21) | @WithJenkinsConfiguredWithCode
    method shouldSupportConfigurationAsCode (line 24) | @Test
    method shouldExportConfigurationAsCode (line 37) | @Test

FILE: src/test/java/hudson/plugins/jira/CredentialsHelperTest.java
  class CredentialsHelperTest (line 28) | @WithJenkins
    method lookupSystemCredentials (line 31) | @Test
    method lookupSystemCredentialsWithDomainRestriction (line 43) | @Test
    method migrateCredentials (line 58) | @Test
    method migrateCredentialsWithExsitingCredentials (line 72) | @Test

FILE: src/test/java/hudson/plugins/jira/DescriptorImplTest.java
  class DescriptorImplTest (line 48) | @WithJenkins
    method doFillCredentialsIdItems (line 61) | @Test
    method listBoxModelContainsName (line 112) | private boolean listBoxModelContainsName(ListBoxModel options, String ...
    method validateFormConnectionErrors (line 119) | @Test
    method validateFormConnectionOK (line 196) | @Test

FILE: src/test/java/hudson/plugins/jira/EmptyFriendlyURLConverterTest.java
  class EmptyFriendlyURLConverterTest (line 17) | @WithJenkins
    method shouldHandleURLClass (line 22) | @Test
    method shouldHandleStringClass (line 29) | @Test
    method shouldHandleNull (line 37) | @Test
    method shouldHandleEmptyString (line 43) | @Test
    method shouldHandleNullAsString (line 49) | @Test
    method shouldHandleMalformedUrlAsString (line 58) | @Test

FILE: src/test/java/hudson/plugins/jira/EnvironmentExpanderTest.java
  class EnvironmentExpanderTest (line 17) | class EnvironmentExpanderTest {
    method createCharacteristicEnvironment (line 28) | @BeforeEach
    method returnVariableWhenValueNotFound (line 38) | @Test
    method returnValueWhenFound (line 44) | @Test
    method returnVariableFromNullRunEnvironment (line 54) | @Test
    method returnValueFromRunEnvironment (line 60) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraBuildActionTest.java
  class JiraBuildActionTest (line 18) | class JiraBuildActionTest {
    method binaryCompatibility (line 24) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraChangeLogAnnotatorTest.java
  class JiraChangeLogAnnotatorTest (line 35) | @ExtendWith(MockitoExtension.class)
    method before (line 48) | @BeforeEach
    method annotate (line 62) | @Test
    method annotateDisabledOnSiteLevel (line 78) | @Test
    method annotateWf (line 91) | @Test
    method wordBoundaryProblem (line 112) | @Test
    method matchMultipleIssueIds (line 140) | @Test
    method hasProjectForIssueIsCaseInsensitive (line 155) | @Test
    method caseInsensitiveAnnotate (line 169) | @Test
    method getIssueDetailsForMissingIssues (line 185) | @Test
    method invalidUserPattern (line 205) | @Test
    method matchOnlyMatchGroup1 (line 223) | @Test
    method alternativeURLAnnotate (line 249) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraCreateIssueNotifierTest.java
  class JiraCreateIssueNotifierTest (line 45) | @WithJenkins
    method createCommonMocks (line 71) | @BeforeEach
    method performSuccessFailure (line 98) | @Test
    method performSuccessFailureWithEnv (line 122) | @Test
    method performFailureFailure (line 146) | @Test
    method performFailureSuccessIssueOpen (line 190) | @Test
    method performFailureSuccessIssueClosedWithComponents (line 237) | @Test
    method isDone (line 275) | @Test
    method doFillPriorityIdItems (line 287) | @Test
    method doFillTypeItems (line 359) | @Test
    method testCreateIssueNotifierExceptionLogging (line 431) | @Test
    method newFolder (line 456) | private static File newFolder(File root, String... subDirs) throws IOE...

FILE: src/test/java/hudson/plugins/jira/JiraCreateReleaseNotesTest.java
  class JiraCreateReleaseNotesTest (line 39) | @ExtendWith(MockitoExtension.class)
    method createCommonMocks (line 75) | @BeforeEach
    method defaults (line 98) | @Test
    method jiraApiCallDefaultFilter (line 105) | @Test
    method jiraApiCallOtherFilter (line 113) | @Test
    method failBuildOnErrorEmptyProjectKey (line 125) | @Test
    method failBuildOnErrorEmptyRelease (line 136) | @Test
    method releaseNotesContent (line 146) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraEnvironmentContributingActionTest.java
  class JiraEnvironmentContributingActionTest (line 15) | class JiraEnvironmentContributingActionTest {
    method buildEnvVarsEnvIsNull (line 20) | @Test
    method passedVariablesAreNull (line 30) | @Test
    method buildEnvVarsAddVariables (line 40) | @Test
    method noExceptionWhenNullsPassed (line 63) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraEnvironmentVariableBuilderTest.java
  class JiraEnvironmentVariableBuilderTest (line 33) | @WithJenkins
    method createMocks (line 55) | @BeforeEach
    method testIssueSelectorDefaultsToDefault (line 77) | @Test
    method testSetIssueSelectorPersists (line 84) | @Test
    method testPerformWithNoSiteFailsBuild (line 91) | @Test
    method testPerformAddsAction (line 100) | @Test
    method testHasIssueSelectors_HasDefaultSelector (line 121) | @Test
    method testHasIssueSelectors (line 130) | @Test
    method testEnvBuilderExceptionLogging (line 140) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraFolderPropertyTest.java
  class JiraFolderPropertyTest (line 18) | @WithJenkins
    method configRoundtrip (line 21) | @Test
    method getFolderStore (line 39) | public static CredentialsStore getFolderStore(Folder f) {

FILE: src/test/java/hudson/plugins/jira/JiraGlobalConfigurationSaveTest.java
  class JiraGlobalConfigurationSaveTest (line 16) | @WithJenkins
    method jiraSitesListSaved (line 19) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraGlobalConfigurationTest.java
  class JiraGlobalConfigurationTest (line 13) | @WithJenkins
    method migrateOldConfiguration (line 16) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraIssueMigratorTest.java
  class JiraIssueMigratorTest (line 24) | class JiraIssueMigratorTest {
    method prepareMocks (line 38) | @BeforeEach
    method addingVersion (line 56) | @Test
    method migratingToVersion (line 68) | @Test
    method replacingVersion (line 79) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraIssueParameterDefResultTest.java
  class JiraIssueParameterDefResultTest (line 14) | class JiraIssueParameterDefResultTest {
    method prepareMocks (line 18) | @BeforeEach
    method testSummaryResult (line 35) | @Test
    method testAltSummaryResultCommaSep (line 42) | @Test
    method testAltSummaryResultCommaSpaceSep (line 50) | @Test
    method testAltSummaryResultMissingFieldIgnored (line 58) | @Test
    method testAltSummaryResultEmptyFieldIgnored (line 66) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraIssueUpdateBuilderTest.java
  class JiraIssueUpdateBuilderTest (line 26) | class JiraIssueUpdateBuilderTest {
    method createMocks (line 39) | @BeforeEach
    method performNoSite (line 64) | @Test
    method validateFailureResult (line 72) | @Test
    method performProgressFails (line 84) | @Test
    method performProgressOK (line 93) | @Test
    method testPipelineWithJiraSite (line 102) | @WithJenkins
    method testIssueUpdateBuilderRestException (line 116) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraIssueUpdaterTest.java
  class JiraIssueUpdaterTest (line 24) | class JiraIssueUpdaterTest {
    method issueSelectorDefaultsToDefault (line 26) | @Test
    method setIssueSelectorPersists (line 32) | @Test
    method setScmPersists (line 46) | @Test
    method setLabelsPersists (line 60) | @Test
    method testPipeline (line 68) | @WithJenkins

FILE: src/test/java/hudson/plugins/jira/JiraJobActionTest.java
  class JiraJobActionTest (line 21) | @WithJenkins
    method setup (line 32) | @BeforeEach
    method detectBranchNameIssue (line 41) | @Test
    method detectBranchNameIssueWithEncodedJobName (line 52) | @Test
    method detectBranchNameIssueJustIssueKey (line 64) | @Test
    method detectBranchNameIssueNoIssueKey (line 76) | @Test
    method testJobActionRestException (line 84) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraProjectPropertyTest.java
  class JiraProjectPropertyTest (line 16) | @WithJenkinsConfiguredWithCode
    method initialize (line 25) | @BeforeEach
    method getSitesNullWithoutFolder (line 36) | @Test
    method getSitesNullWithFolder (line 46) | @Test
    method getSiteFromProjectProperty (line 56) | @Test
    method getSiteFromSingleEntry (line 66) | @Test
    method getSiteFromFirstGlobalMultipleEntryMultipleSites (line 80) | @Test
    method getSiteFromSecondGlobalEntryMultipleSites (line 94) | @Test
    method getSiteFromFirstFolderLayer (line 108) | @Test
    method getSiteFromNestedFolderLayer (line 122) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraReleaseVersionUpdateBuilderTest.java
  class JiraReleaseVersionUpdateBuilderTest (line 15) | class JiraReleaseVersionUpdateBuilderTest {
    method createMocks (line 19) | @BeforeEach
    method testPipeline (line 24) | @WithJenkins

FILE: src/test/java/hudson/plugins/jira/JiraRestServiceProxyTest.java
  class JiraRestServiceProxyTest (line 24) | @WithJenkins
    method prepare (line 36) | @BeforeEach
    method dispose (line 44) | @AfterEach
    method withProxy (line 51) | @Test
    method withProxyAndNoProxyHosts (line 65) | @Test
    method withoutProxy (line 74) | @Test
    method getProxyObjectFromRequest (line 79) | private Object getProxyObjectFromRequest()

FILE: src/test/java/hudson/plugins/jira/JiraRestServiceTest.java
  class JiraRestServiceTest (line 25) | class JiraRestServiceTest {
    method createMocks (line 35) | @BeforeEach
    method baseApiPath (line 47) | @Test
    method getIssuesFromJqlSearchRestException (line 57) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraSessionTest.java
  class JiraSessionTest (line 34) | @ExtendWith(MockitoExtension.class)
    method prepareMocks (line 48) | @BeforeEach
    method replaceWithFixVersionByRegex (line 53) | @Test
    method replaceFixVersion (line 91) | @Test
    method getIssue (line 131) | private Issue getIssue(List<String> versions, long id) throws URISynta...
    method shouldAddVersionToAllIssues (line 177) | @Test
    method shouldAddVersionWhenNoFixVersions (line 209) | @Test
    method shouldNotCallUpdateIfNoIssues (line 230) | @Test
    method shouldReturnIfVersionNotFound (line 244) | @Test

FILE: src/test/java/hudson/plugins/jira/JiraSiteSecurity1029Test.java
  class JiraSiteSecurity1029Test (line 45) | @WithJenkins
    method cannotLeakCredentials (line 52) | @Test
    method setupServer (line 241) | public void setupServer(JenkinsRule j) throws Exception {
    method stopEmbeddedHttpServer (line 256) | @AfterEach
    class FakeJiraServlet (line 261) | private static class FakeJiraServlet implements HttpHandler {
      method FakeJiraServlet (line 268) | FakeJiraServlet(JenkinsRule jenkinsRule) {
      method setServerUrl (line 272) | public void setServerUrl(URI serverUri) {
      method getPasswordAndReset (line 276) | public String getPasswordAndReset() {
      method handle (line 282) | @Override
      method myPermissions (line 306) | private void myPermissions(HttpExchange he) throws IOException {

FILE: src/test/java/hudson/plugins/jira/JiraSiteTest.java
  class JiraSiteTest (line 44) | @WithJenkins
    method init (line 54) | @BeforeEach
    method createSessionWithProvidedCredentials (line 60) | @Test
    method createSessionWithGlobalCredentials (line 79) | @Test
    method createSessionReturnsNullIfCredentialsIsNull (line 99) | @Test
    method deserializeMigrateCredentials (line 118) | @Test
    method deserializeNormal (line 151) | @Test
    method deserializeWithoutCredentials (line 176) | @WithoutJenkins
    class JiraSiteOld (line 193) | private static class JiraSiteOld extends JiraSite {
      method JiraSiteOld (line 197) | JiraSiteOld(
    method alternativeURLNotNull (line 226) | @Test
    method ensureUrlEndsWithSlash (line 244) | @Test
    method urlNulls (line 257) | @Test
    method toUrlConvertsEmptyStringToNull (line 266) | @Test
    method toUrlConvertsOnlyWhitespaceToNull (line 273) | @Test
    method ensureMainUrlIsMandatory (line 280) | @WithoutJenkins
    method ensureAlternativeUrlIsNotMandatory (line 288) | @Test
    method malformedUrl (line 296) | @WithoutJenkins
    method malformedAlternativeUrl (line 304) | @WithoutJenkins
    method credentialsAreNullByDefault (line 311) | @Test
    method credentials (line 319) | @Test
    method siteAsProjectProperty (line 342) | @Test
    method projectPropertySiteAndParentBothNull (line 354) | @Test
    method noProjectProperty (line 368) | @Test
    method noProjectPropertyUpFoldersWithNoProperty (line 375) | @Test
    method noProjectPropertyFindFolderPropertyWithNullZeroLengthAndValidSites (line 395) | @Test
    method siteConfiguredGlobally (line 418) | @Test
    method getIssueWithoutSession (line 428) | @Test
    method ensureMaxIssuesFromJqlEndsUpMaxAllowed (line 438) | @Test
    method createFolder (line 446) | private Folder createFolder(JenkinsRule j, Folder folder) throws IOExc...

FILE: src/test/java/hudson/plugins/jira/JiraVersionCreatorBuilderTest.java
  class JiraVersionCreatorBuilderTest (line 23) | class JiraVersionCreatorBuilderTest {
    method createMocks (line 31) | @BeforeEach
    method testPipelineWithJiraSite (line 37) | @WithJenkins
    method readResolveSetsFailIfAlreadyExistsWhenMissingInConfig (line 51) | @Test
    method readResolvePresentInConfig (line 77) | @Test

FILE: src/test/java/hudson/plugins/jira/MailResolverDisabledTest.java
  class MailResolverDisabledTest (line 41) | @WithJenkins
    method setUp (line 44) | @BeforeAll
    method disableEmailResolver (line 49) | @Test

FILE: src/test/java/hudson/plugins/jira/MailResolverWithExtensionTest.java
  class MailResolverWithExtensionTest (line 52) | @WithJenkins
    method createMocks (line 64) | @BeforeEach
    method emailResolverWithSecurityExtension (line 79) | @Test
    class DummySecurityListener (line 91) | @TestExtension
      method authenticated2 (line 93) | @Override
      method authenticated (line 98) | @Override
      method check (line 103) | private void check(String userId) {

FILE: src/test/java/hudson/plugins/jira/MockAffectedFile.java
  type MockAffectedFile (line 8) | public interface MockAffectedFile extends AffectedFile {}

FILE: src/test/java/hudson/plugins/jira/UnmaskMailTest.java
  class UnmaskMailTest (line 12) | class UnmaskMailTest {
    method unmaskMailTest (line 14) | @Test
    method test (line 47) | private void test(String expected, String masked) {

FILE: src/test/java/hudson/plugins/jira/UpdaterTest.java
  class UpdaterTest (line 61) | @SuppressWarnings("unchecked")
    class MockEntry (line 67) | private static class MockEntry extends Entry {
      method MockEntry (line 71) | MockEntry(String msg) {
      method getAffectedPaths (line 75) | @Override
      method getAuthor (line 80) | @Override
      method getMsg (line 85) | @Override
    method prepare (line 91) | @BeforeEach
    method getScmCommentsFromPreviousBuilds (line 97) | @Test
    method comment (line 162) | @Test
    method issueIsRemovedFromCarryOverListAfterSubmission (line 224) | @Test
    method getChangesUsingReflectionForWorkflowJob (line 299) | @Test
    method getChangesUsingReflectionForunknownJob (line 312) | @WithoutJenkins
    method appendChangeTimestampToDescription (line 323) | @Test
    method dateTimeInChangeDescription (line 341) | @Test
    method appendChangeTimestampToDescriptionNullFormat (line 377) | @Test
    method appendChangeTimestampToDescriptionNoFormat (line 402) | @Test
    method tesDescriptionWithAffectedFiles (line 427) | @Test

FILE: src/test/java/hudson/plugins/jira/VersionCreatorTest.java
  class VersionCreatorTest (line 34) | @ExtendWith(MockitoExtension.class)
    method createMocks (line 74) | @BeforeEach
    method callsJiraWithSpecifiedParameters (line 92) | @Test
    method expandsEnvParameters (line 120) | @Test
    method buildDidNotFailWhenVersionExists (line 147) | @Test
    method buildDoesNotFailWhenVersionExistsAndFailIfAlreadyExistsIsFalse (line 160) | @Test

FILE: src/test/java/hudson/plugins/jira/VersionReleaserTest.java
  class VersionReleaserTest (line 32) | @ExtendWith(MockitoExtension.class)
    method createMocks (line 74) | @BeforeEach
    method callsJiraWithSpecifiedParameters (line 96) | @Test
    method expandsEnvParameters (line 110) | @Test
    method buildDidNotFailWhenVersionExists (line 124) | @Test

FILE: src/test/java/hudson/plugins/jira/auth/BearerHttpAuthenticationHandlerTest.java
  class BearerHttpAuthenticationHandlerTest (line 9) | class BearerHttpAuthenticationHandlerTest {
    method testConfigure (line 11) | @Test

FILE: src/test/java/hudson/plugins/jira/auth/JiraRestServiceBearerAuthTest.java
  class JiraRestServiceBearerAuthTest (line 27) | class JiraRestServiceBearerAuthTest {
    method createMocks (line 36) | @BeforeEach
    method baseApiPath (line 48) | @Test
    method getIssuesFromJqlSearchTimeout (line 58) | @Test

FILE: src/test/java/hudson/plugins/jira/listissuesparameter/JiraIssueParameterDefinitionTest.java
  class JiraIssueParameterDefinitionTest (line 32) | @ExtendWith(MockitoExtension.class)
    method createValueInvalidParameters (line 38) | static Stream<Arguments> createValueInvalidParameters() {
    method shouldCreateNullParameterForInvalidValues (line 45) | @ParameterizedTest
    method shouldCreateValue (line 56) | @Test
    class DescriptorImplTest (line 67) | @Nested
      method shouldFillValueItems (line 72) | @Test
      method shouldNotFillValueItemsIfPermissionMissing (line 95) | @Test
      method shouldHaveNoSearchMatchesItemIfSearchMatchesNoItem (line 106) | @Test

FILE: src/test/java/hudson/plugins/jira/listissuesparameter/JiraIssueParameterTest.java
  class JiraIssueParameterTest (line 22) | @WithJenkins
    method scriptedPipeline (line 25) | @Test
    method nullValueDoesNotThrowException (line 47) | @Test
    method nonNullValueInBuildEnvironment (line 65) | @Test
    method variableResolverHandlesNullAndNonNullValues (line 80) | @Test
    method originalNullPointerExceptionScenarioFixed (line 101) | @Test

FILE: src/test/java/hudson/plugins/jira/pipeline/CommentStepTest.java
  class CommentStepTest (line 30) | @WithJenkins
    method setUp (line 38) | @BeforeEach
    method configRoundTrip (line 44) | @Test
    method configRoundTrip (line 49) | private void configRoundTrip(String issueKey, String body) throws Exce...
    method callSessionAddComment (line 57) | @Test
    method addCommentRestException (line 105) | @Test

FILE: src/test/java/hudson/plugins/jira/pipeline/IssueFieldUpdateStepTest.java
  class IssueFieldUpdateStepTest (line 40) | @WithJenkinsConfiguredWithCode
    method before (line 72) | @BeforeEach
    method checkPrepareFieldId (line 85) | @Test
    method shouldFailIfSelectorIsNull (line 98) | @Test
    method checkSubmit (line 105) | @Test
    method testPipeline (line 142) | @Test
    method issueFieldFindIssueIdsRestException (line 155) | @Test
    method issueFieldSubmitFieldsRestException (line 191) | @Test

FILE: src/test/java/hudson/plugins/jira/pipeline/IssueSelectorStepTest.java
  class IssueSelectorStepTest (line 29) | @WithJenkins
    method setUp (line 54) | @BeforeEach
    method runWithNullSite (line 67) | @Test
    method run (line 79) | @Test
    method runWithRestException (line 93) | @Test

FILE: src/test/java/hudson/plugins/jira/pipeline/SearchIssuesStepTest.java
  class SearchIssuesStepTest (line 29) | @WithJenkins
    method setUp (line 37) | @BeforeEach
    method configRoundTrip (line 43) | @Test
    method configRoundTrip (line 49) | private void configRoundTrip(String jql) throws Exception {
    method callGetIssuesFromJqlSearch (line 54) | @Test
    method getIssuesFromJqlSearchRestException (line 97) | @Test

FILE: src/test/java/hudson/plugins/jira/selector/DefaultIssueSelectorTest.java
  class DefaultIssueSelectorTest (line 30) | class DefaultIssueSelectorTest {
    class MockEntry (line 32) | private static class MockEntry extends Entry {
      method MockEntry (line 36) | MockEntry(String msg) {
      method getAffectedPaths (line 40) | @Override
      method getAuthor (line 45) | @Override
      method getMsg (line 50) | @Override
    method projectNamesAllowed (line 56) | @Test
    method findIssuesWithJiraParameters (line 112) | @Test
    method userPatternNotMatch (line 150) | @Test
    method userPatternMatchTwoIssuesInOneComment (line 166) | @Test
    method userPatternMatch (line 192) | @Test
    method defaultPatternNotToMatchMavenRelease (line 221) | @Test

FILE: src/test/java/hudson/plugins/jira/selector/ExplicitIssueSelectorTest.java
  class ExplicitIssueSelectorTest (line 11) | class ExplicitIssueSelectorTest {
    method returnsExplicitCollections (line 15) | @Test

FILE: src/test/java/hudson/plugins/jira/selector/JqlIssueSelectorTest.java
  class JqlIssueSelectorTest (line 25) | @ExtendWith(MockitoExtension.class)
    method prepare (line 42) | @BeforeEach
    method dontDependOnRunAndTaskListener (line 48) | @Test
    method callGetIssuesFromJqlSearch (line 55) | @Test

FILE: src/test/java/hudson/plugins/jira/selector/perforce/JobIssueSelectorTest.java
  class JobIssueSelectorTest (line 24) | public abstract class JobIssueSelectorTest {
    method createJobIssueSelector (line 26) | protected abstract JobIssueSelector createJobIssueSelector();
    method findsIssuesWithJiraParameters (line 28) | @Test
    method findsCarriedOnIssues (line 66) | @Test

FILE: src/test/java/hudson/plugins/jira/selector/perforce/P4JobIssueSelectorTest.java
  class P4JobIssueSelectorTest (line 21) | class P4JobIssueSelectorTest extends JobIssueSelectorTest {
    method findsTwoP4Jobs (line 23) | @Test
    method createJobIssueSelector (line 66) | @Override

FILE: src/test/java/hudson/plugins/jira/versionparameter/JiraReleaseVersionParameterTest.java
  class JiraReleaseVersionParameterTest (line 13) | @WithJenkins
    method scriptedPipeline (line 16) | @Test

FILE: src/test/java/hudson/plugins/jira/versionparameter/JiraVersionParameterDefinitionTest.java
  class JiraVersionParameterDefinitionTest (line 38) | class JiraVersionParameterDefinitionTest {
    method createMocksAndVersions (line 54) | @BeforeEach
    method parameterValueMethodOverrides (line 70) | @Test
    method createValueInvalidParameters (line 89) | static Stream<Arguments> createValueInvalidParameters() {
    method shouldCreateNullParameterForInvalidValues (line 96) | @ParameterizedTest
    method shouldCreateValue (line 110) | @Test
    method showReleasedVersions (line 124) | @Test
    method showUnreleasedVersions (line 140) | @Test
    method showArchivedVersions (line 156) | @Test
    method showAllVersions (line 173) | @Test
    method showReleasedUnreleasedVersions (line 190) | @Test
    method showReleasedArchivedVersions (line 207) | @Test
    method showUnreleasedArchivedVersions (line 224) | @Test
    method equalResults (line 241) | @Test
    method diffResults (line 248) | @Test
    method nullResultCompare (line 255) | @Test
    method diffClassResultCompare (line 262) | @Test
    method sameNameDiffIdResultCompare (line 268) | @Test
    method compareResultEqHashCode (line 276) | @Test
    method compareResultNotEqHashCode (line 283) | @Test
    method getJiraShowUnreleasedOn (line 290) | @Test
    method withJiraStaticMocks (line 297) | private void withJiraStaticMocks(Runnable testLogic) {
    class DescriptorImplTest (line 313) | @Nested
      method shouldFillVersionItems (line 319) | @Test
      method shouldNotFillVersionsItemsIfPermissionMissing (line 340) | @Test
      method shouldHaveNoSearchMatchesItemIfSearchMatchesNoItem (line 351) | @Test

FILE: src/test/java/hudson/plugins/jira/versionparameter/VersionComparatorTest.java
  class VersionComparatorTest (line 13) | class VersionComparatorTest {
    method complexCompare (line 15) | @Test
    method singleComparisonsTests (line 59) | @Test
    method compare (line 84) | private int compare(String v1, String v2) {
Condensed preview — 300 files, each showing path, character count, and a content snippet. Download the .json file or copy for the full structured content (849K chars).
[
  {
    "path": ".git-blame-ignore-revs",
    "chars": 103,
    "preview": "# .git-blame-ignore-revs\n# Reformatting of code with Spotless\n969d12b2b997f23561af51530f9394e8ca34dfd7\n"
  },
  {
    "path": ".github/CODEOWNERS",
    "chars": 36,
    "preview": "* @jenkinsci/jira-plugin-developers\n"
  },
  {
    "path": ".github/FUNDING.yml",
    "chars": 653,
    "preview": "# These are supported funding model platforms\n\ngithub: [ olamy, rantoniuk]\npatreon: # Replace with a single Patreon user"
  },
  {
    "path": ".github/ISSUE_TEMPLATE/1-report-bug.yml",
    "chars": 3018,
    "preview": "name: \"🐛 Bug report\"\ntype: \"Bug\"\ndescription: Create a bug report to help us improve\n\nbody:\n  - type: markdown\n    attri"
  },
  {
    "path": ".github/ISSUE_TEMPLATE/2-feature-request.yml",
    "chars": 438,
    "preview": "name: \"🚀 Feature request\"\ntype: \"feature\"\ndescription: I have a suggestion\n\nbody:\n  - type: textarea\n    attributes:\n   "
  },
  {
    "path": ".github/ISSUE_TEMPLATE/3-documentation.yml",
    "chars": 563,
    "preview": "name: \"📝 Documentation\"\nlabels: [\"documentation\"]\ndescription: \"Let us know if any documentation is missing or could be "
  },
  {
    "path": ".github/ISSUE_TEMPLATE/config.yml",
    "chars": 313,
    "preview": "blank_issues_enabled: true\ncontact_links:\n  - name: Community forum\n    url: https://community.jenkins.io/\n    about: Pl"
  },
  {
    "path": ".github/pull_request_template.md",
    "chars": 965,
    "preview": "<!--\nPut an `x` into the [ ] to show you have filled the information\n-->\n\n### Related issue\n\n<!-- Paste links to the iss"
  },
  {
    "path": ".github/release-drafter.yml",
    "chars": 340,
    "preview": "_extends: github:jenkinsci/.github:/.github/release-drafter.yml\nname-template: $RESOLVED_VERSION\ntag-template: jira-$RES"
  },
  {
    "path": ".github/renovate.json",
    "chars": 743,
    "preview": "{\n  \"$schema\": \"https://docs.renovatebot.com/renovate-schema.json\",\n  \"extends\": [\n    \"github>jenkinsci/renovate-config"
  },
  {
    "path": ".github/workflows/crowdin.yml",
    "chars": 1031,
    "preview": "---\nname: Crowdin\n\non:\n  push:\n    branches:\n      - master\n  workflow_dispatch:\n\npermissions:\n  actions: write\n  conten"
  },
  {
    "path": ".github/workflows/jenkins-security-scan.yml",
    "chars": 602,
    "preview": "name: Jenkins Security Scan\n\non:\n  push:\n    branches:\n      - master\n  pull_request:\n    types: [ opened, synchronize, "
  },
  {
    "path": ".github/workflows/release-drafter.yml",
    "chars": 239,
    "preview": "name: Release Drafter\non:\n  push:\n    branches:\n      - master\njobs:\n  update_release_draft:\n    runs-on: ubuntu-latest\n"
  },
  {
    "path": ".github/workflows/sonarcloud.yml",
    "chars": 920,
    "preview": "name: SonarCloud analysis\n\non:\n  push:\n    branches: [ \"master\" ]\n    tags:\n      - 'jira*'\n  pull_request:\n    branches"
  },
  {
    "path": ".gitignore",
    "chars": 224,
    "preview": ".classpath\n.project\n.settings\n.factorypath\nbuild\ntarget\nbin\nwork/\n.work\n.env*\n.docker\n*.code-workspace\n\n# ignore all Ide"
  },
  {
    "path": ".mvn/extensions.xml",
    "chars": 416,
    "preview": "<extensions xmlns=\"http://maven.apache.org/EXTENSIONS/1.0.0\" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xsi:s"
  },
  {
    "path": ".mvn/maven.config",
    "chars": 52,
    "preview": "-Pconsume-incrementals\n-Pmight-produce-incrementals\n"
  },
  {
    "path": ".pre-commit-config.yaml",
    "chars": 336,
    "preview": "repos:\n  - repo: https://github.com/pre-commit/pre-commit-hooks\n    rev: v4.6.0\n    hooks:\n      - id: check-yaml\n      "
  },
  {
    "path": "CONTRIBUTING.md",
    "chars": 2171,
    "preview": "# Contribution guidelines\n\nGeneral rules:\n\n- check the [general Jenkins development guide](https://www.jenkins.io/doc/de"
  },
  {
    "path": "Jenkinsfile",
    "chars": 484,
    "preview": "/*\n See the documentation for more options:\n https://github.com/jenkins-infra/pipeline-library/\n*/\nbuildPlugin(\n  forkCo"
  },
  {
    "path": "LICENSE.md",
    "chars": 1109,
    "preview": "The MIT License\n\nCopyright (c) 2007, Kohsuke Kawaguchi and jira-plugin contributors\n\nPermission is hereby granted, free "
  },
  {
    "path": "README.md",
    "chars": 4251,
    "preview": "# Jenkins Jira Plugin\n\n[![Jenkins Version](https://img.shields.io/badge/Jenkins-2.479.3-green.svg?label=min.%20Jenkins)]"
  },
  {
    "path": "crowdin.yml",
    "chars": 421,
    "preview": "---\n\nfiles:\n  - source: '/src/main/resources/hudson/plugins/jira/**/*.properties'\n    ignore:\n      - '/src/main/resourc"
  },
  {
    "path": "docker-compose.yml",
    "chars": 1385,
    "preview": "#  docker compose up -d --build --force-recreate\nservices:\n    jenkins:\n        image: jenkins/jenkins:lts\n        resta"
  },
  {
    "path": "docs/.nojekyll",
    "chars": 0,
    "preview": ""
  },
  {
    "path": "docs/README.md",
    "chars": 2198,
    "preview": "# Jenkins Jira plugin\n\nThis plugin integrates with Jenkins the [Atlassian Jira Software](http://www.atlassian.com/softwa"
  },
  {
    "path": "docs/_sidebar.md",
    "chars": 188,
    "preview": "* [Home](/)\n* [Features](features.md)\n* [System Properties](system-properties.md)\n* [Usage Examples](usage-examples.md)\n"
  },
  {
    "path": "docs/changelog.md",
    "chars": 12875,
    "preview": "Changelog\n===\n\n### Newer versions\n\nSee [GitHub releases](https://github.com/jenkinsci/jira-plugin/releases)\n\n### Unrelea"
  },
  {
    "path": "docs/features.md",
    "chars": 3672,
    "preview": "# Jenkins Jira plugin features\n\n### Using Jira REST API\n\nThis plugin has an optional feature to update Jira issues with "
  },
  {
    "path": "docs/index.html",
    "chars": 949,
    "preview": "<!DOCTYPE html>\n<html lang=\"en\">\n<head>\n  <meta charset=\"UTF-8\">\n  <title>Document</title>\n  <meta http-equiv=\"X-UA-Comp"
  },
  {
    "path": "docs/system-properties.md",
    "chars": 424,
    "preview": "# System Properties\n\nThere are some cases when you might want to change the plugin's behavior globally, by overriding [J"
  },
  {
    "path": "docs/troubleshooting.md",
    "chars": 1543,
    "preview": "# Common issues\n\n## Adding a custom Log Recorder\n\nTo help debug any issues with this plugin, it's useful to look at more"
  },
  {
    "path": "docs/usage-examples.md",
    "chars": 3723,
    "preview": "# Usage examples\n\n## jiraCommentIssues usage example\n\nYou need keep reference to used scm.\nAs an example, you can write "
  },
  {
    "path": "pom.xml",
    "chars": 14842,
    "preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project xmlns=\"http://maven.apache.org/POM/4.0.0\" xmlns:xsi=\"http://www.w3.org/2"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/ApacheAsyncHttpClient.java",
    "chars": 23527,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport static io.atlassian.util.concurrent.Promises.rejected;\ni"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/CommonBuilder.java",
    "chars": 1984,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport com.atlassian.httpclient.api.Common;\nimport java.io.Inpu"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/CompletableFuturePromiseHttpPromiseAsyncClient.java",
    "chars": 6802,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport com.atlassian.sal.api.executor.ThreadLocalContextManager"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/DefaultHttpClientFactory.java",
    "chars": 2529,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport com.atlassian.event.api.EventPublisher;\nimport com.atlas"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/DefaultMessage.java",
    "chars": 4435,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport com.atlassian.httpclient.api.Message;\nimport io.atlassia"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/DefaultRequest.java",
    "chars": 8231,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport static com.atlassian.httpclient.api.Request.Method.DELET"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/DefaultResponse.java",
    "chars": 6403,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport com.atlassian.httpclient.api.Response;\nimport io.atlassi"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/EntityByteArrayInputStream.java",
    "chars": 365,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport java.io.ByteArrayInputStream;\n\npublic class EntityByteAr"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/Headers.java",
    "chars": 4094,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport com.atlassian.httpclient.api.Buildable;\nimport java.nio."
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/MavenUtils.java",
    "chars": 1180,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport static java.lang.String.format;\n\nimport java.io.InputStr"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/PromiseHttpAsyncClient.java",
    "chars": 356,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport io.atlassian.util.concurrent.Promise;\nimport org.apache."
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/RedirectStrategy.java",
    "chars": 2426,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport java.net.URI;\nimport org.apache.http.HttpEntityEnclosing"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/apache/httpcomponents/RequestEntityEffect.java",
    "chars": 2153,
    "preview": "package com.atlassian.httpclient.apache.httpcomponents;\n\nimport com.atlassian.httpclient.api.Request;\nimport io.atlassia"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/base/event/AbstractHttpRequestEvent.java",
    "chars": 1347,
    "preview": "package com.atlassian.httpclient.base.event;\n\nimport java.util.Map;\n\nabstract class AbstractHttpRequestEvent {\n    priva"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/base/event/HttpRequestCompletedEvent.java",
    "chars": 383,
    "preview": "package com.atlassian.httpclient.base.event;\n\nimport java.util.Map;\n\npublic final class HttpRequestCompletedEvent extend"
  },
  {
    "path": "src/main/java/com/atlassian/httpclient/base/event/HttpRequestFailedEvent.java",
    "chars": 568,
    "preview": "package com.atlassian.httpclient.base.event;\n\nimport java.util.Map;\n\npublic final class HttpRequestFailedEvent extends A"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/CredentialsHelper.java",
    "chars": 6552,
    "preview": "package hudson.plugins.jira;\n\nimport com.cloudbees.plugins.credentials.CredentialsMatchers;\nimport com.cloudbees.plugins"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/EmptyFriendlyURLConverter.java",
    "chars": 892,
    "preview": "package hudson.plugins.jira;\n\nimport java.net.MalformedURLException;\nimport java.net.URL;\nimport java.util.logging.Level"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/EnvironmentExpander.java",
    "chars": 902,
    "preview": "package hudson.plugins.jira;\n\nimport hudson.EnvVars;\nimport hudson.model.Run;\nimport hudson.model.TaskListener;\nimport j"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraBuildAction.java",
    "chars": 2445,
    "preview": "package hudson.plugins.jira;\n\nimport edu.umd.cs.findbugs.annotations.NonNull;\nimport hudson.model.Run;\nimport hudson.plu"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraCarryOverAction.java",
    "chars": 1108,
    "preview": "package hudson.plugins.jira;\n\nimport hudson.Util;\nimport hudson.model.InvisibleAction;\nimport hudson.plugins.jira.model."
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraChangeLogAnnotator.java",
    "chars": 5673,
    "preview": "package hudson.plugins.jira;\n\nimport hudson.Extension;\nimport hudson.MarkupText;\nimport hudson.Util;\nimport hudson.model"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraCreateIssueNotifier.java",
    "chars": 19445,
    "preview": "package hudson.plugins.jira;\n\nimport static hudson.plugins.jira.JiraRestService.BUG_ISSUE_TYPE_ID;\n\nimport com.atlassian"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraCreateReleaseNotes.java",
    "chars": 5129,
    "preview": "package hudson.plugins.jira;\n\nimport static org.apache.commons.lang3.StringUtils.defaultIfEmpty;\nimport static org.apach"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraEnvironmentContributingAction.java",
    "chars": 1612,
    "preview": "package hudson.plugins.jira;\n\nimport edu.umd.cs.findbugs.annotations.Nullable;\nimport hudson.EnvVars;\nimport hudson.mode"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraEnvironmentVariableBuilder.java",
    "chars": 3170,
    "preview": "package hudson.plugins.jira;\n\nimport com.atlassian.jira.rest.client.api.RestClientException;\nimport hudson.Extension;\nim"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraFolderProperty.java",
    "chars": 1846,
    "preview": "package hudson.plugins.jira;\n\nimport com.cloudbees.hudson.plugins.folder.AbstractFolder;\nimport com.cloudbees.hudson.plu"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraGlobalConfiguration.java",
    "chars": 1013,
    "preview": "package hudson.plugins.jira;\n\nimport edu.umd.cs.findbugs.annotations.NonNull;\nimport edu.umd.cs.findbugs.annotations.Sup"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraIssueMigrator.java",
    "chars": 5196,
    "preview": "package hudson.plugins.jira;\n\nimport hudson.Extension;\nimport hudson.Launcher;\nimport hudson.model.AbstractBuild;\nimport"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraIssueUpdateBuilder.java",
    "chars": 5305,
    "preview": "/*\n * Copyright 2012 MeetMe, Inc.\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not u"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraIssueUpdater.java",
    "chars": 4735,
    "preview": "package hudson.plugins.jira;\n\nimport hudson.EnvVars;\nimport hudson.Extension;\nimport hudson.Launcher;\nimport hudson.matr"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraJobAction.java",
    "chars": 4573,
    "preview": "package hudson.plugins.jira;\n\nimport com.atlassian.jira.rest.client.api.RestClientException;\nimport edu.umd.cs.findbugs."
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraMailAddressResolver.java",
    "chars": 2467,
    "preview": "package hudson.plugins.jira;\n\nimport hudson.Extension;\nimport hudson.model.Job;\nimport hudson.model.User;\nimport hudson."
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraProjectProperty.java",
    "chars": 5180,
    "preview": "package hudson.plugins.jira;\n\nimport com.cloudbees.hudson.plugins.folder.AbstractFolder;\nimport edu.umd.cs.findbugs.anno"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraReleaseVersionUpdater.java",
    "chars": 3433,
    "preview": "package hudson.plugins.jira;\n\nimport hudson.Extension;\nimport hudson.Launcher;\nimport hudson.model.AbstractBuild;\nimport"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraReleaseVersionUpdaterBuilder.java",
    "chars": 3154,
    "preview": "package hudson.plugins.jira;\n\nimport hudson.EnvVars;\nimport hudson.Extension;\nimport hudson.model.AbstractProject;\nimpor"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraRestService.java",
    "chars": 27307,
    "preview": "/*\n * Copyright 2015 Hao Cheng Lee\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not "
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraSession.java",
    "chars": 16587,
    "preview": "package hudson.plugins.jira;\n\nimport static org.apache.commons.lang3.StringUtils.isNotEmpty;\n\nimport com.atlassian.jira."
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraSessionFactory.java",
    "chars": 2534,
    "preview": "package hudson.plugins.jira;\n\nimport com.atlassian.jira.rest.client.auth.BasicHttpAuthenticationHandler;\nimport com.clou"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraSite.java",
    "chars": 56649,
    "preview": "package hudson.plugins.jira;\n\nimport static org.apache.commons.lang3.StringUtils.isEmpty;\nimport static org.apache.commo"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraVersionCreator.java",
    "chars": 3402,
    "preview": "package hudson.plugins.jira;\n\nimport hudson.Extension;\nimport hudson.Launcher;\nimport hudson.model.AbstractBuild;\nimport"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/JiraVersionCreatorBuilder.java",
    "chars": 3614,
    "preview": "package hudson.plugins.jira;\n\nimport hudson.EnvVars;\nimport hudson.Extension;\nimport hudson.model.AbstractProject;\nimpor"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/RunScmChangeExtractor.java",
    "chars": 3436,
    "preview": "package hudson.plugins.jira;\n\nimport hudson.model.AbstractBuild;\nimport hudson.model.AbstractBuild.DependencyChange;\nimp"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/Updater.java",
    "chars": 15651,
    "preview": "package hudson.plugins.jira;\n\nimport static java.lang.String.format;\n\nimport com.atlassian.jira.rest.client.api.RestClie"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/VersionCreator.java",
    "chars": 3641,
    "preview": "package hudson.plugins.jira;\n\nimport static org.apache.commons.lang3.StringUtils.isEmpty;\n\nimport hudson.model.BuildList"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/VersionReleaser.java",
    "chars": 4060,
    "preview": "package hudson.plugins.jira;\n\nimport hudson.model.BuildListener;\nimport hudson.model.Job;\nimport hudson.model.Result;\nim"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/auth/BearerHttpAuthenticationHandler.java",
    "chars": 801,
    "preview": "package hudson.plugins.jira.auth;\n\nimport com.atlassian.httpclient.api.Request.Builder;\nimport com.atlassian.jira.rest.c"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/extension/ExtendedAsynchronousJiraRestClient.java",
    "chars": 1274,
    "preview": "package hudson.plugins.jira.extension;\n\nimport com.atlassian.jira.rest.client.internal.async.AsynchronousJiraRestClient;"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/extension/ExtendedAsynchronousMyPermissionsRestClient.java",
    "chars": 1220,
    "preview": "package hudson.plugins.jira.extension;\n\nimport com.atlassian.httpclient.api.HttpClient;\nimport com.atlassian.jira.rest.c"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/extension/ExtendedAsynchronousVersionRestClient.java",
    "chars": 1354,
    "preview": "package hudson.plugins.jira.extension;\n\nimport com.atlassian.httpclient.api.HttpClient;\nimport com.atlassian.jira.rest.c"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/extension/ExtendedJiraRestClient.java",
    "chars": 303,
    "preview": "package hudson.plugins.jira.extension;\n\nimport com.atlassian.jira.rest.client.api.JiraRestClient;\n\npublic interface Exte"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/extension/ExtendedMyPermissionsRestClient.java",
    "chars": 247,
    "preview": "package hudson.plugins.jira.extension;\n\nimport com.atlassian.jira.rest.client.api.domain.Permissions;\nimport io.atlassia"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/extension/ExtendedVersion.java",
    "chars": 777,
    "preview": "package hudson.plugins.jira.extension;\n\nimport com.atlassian.jira.rest.client.api.domain.Version;\nimport edu.umd.cs.find"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/extension/ExtendedVersionInput.java",
    "chars": 1462,
    "preview": "package hudson.plugins.jira.extension;\n\nimport com.atlassian.jira.rest.client.api.domain.input.VersionInput;\nimport edu."
  },
  {
    "path": "src/main/java/hudson/plugins/jira/extension/ExtendedVersionInputJsonGenerator.java",
    "chars": 1217,
    "preview": "package hudson.plugins.jira.extension;\n\nimport com.atlassian.jira.rest.client.internal.json.JsonParseUtil;\nimport com.at"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/extension/ExtendedVersionJsonParser.java",
    "chars": 1630,
    "preview": "package hudson.plugins.jira.extension;\n\nimport com.atlassian.jira.rest.client.internal.json.JsonObjectParser;\nimport com"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/extension/ExtendedVersionRestClient.java",
    "chars": 498,
    "preview": "package hudson.plugins.jira.extension;\n\nimport com.atlassian.jira.rest.client.api.VersionRestClient;\nimport io.atlassian"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/listissuesparameter/JiraIssueParameterDefinition.java",
    "chars": 6857,
    "preview": "/*\n * Copyright 2011-2012 Insider Guides, Inc., MeetMe, Inc.\n *\n * Licensed under the Apache License, Version 2.0 (the \""
  },
  {
    "path": "src/main/java/hudson/plugins/jira/listissuesparameter/JiraIssueParameterValue.java",
    "chars": 2269,
    "preview": "/*\n * Copyright 2011-2012 Insider Guides, Inc., MeetMe, Inc.\n *\n * Licensed under the Apache License, Version 2.0 (the \""
  },
  {
    "path": "src/main/java/hudson/plugins/jira/model/JiraIssue.java",
    "chars": 2090,
    "preview": "package hudson.plugins.jira.model;\n\nimport com.atlassian.jira.rest.client.api.domain.Issue;\nimport edu.umd.cs.findbugs.a"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/model/JiraIssueField.java",
    "chars": 1605,
    "preview": "package hudson.plugins.jira.model;\n\npublic class JiraIssueField implements Comparable<JiraIssueField> {\n\n    private fin"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/model/JiraVersion.java",
    "chars": 4405,
    "preview": "package hudson.plugins.jira.model;\n\nimport com.atlassian.jira.rest.client.api.domain.Version;\nimport hudson.plugins.jira"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/pipeline/CommentStep.java",
    "chars": 3230,
    "preview": "package hudson.plugins.jira.pipeline;\n\nimport com.atlassian.jira.rest.client.api.RestClientException;\nimport edu.umd.cs."
  },
  {
    "path": "src/main/java/hudson/plugins/jira/pipeline/IssueFieldUpdateStep.java",
    "chars": 6211,
    "preview": "package hudson.plugins.jira.pipeline;\n\nimport com.atlassian.jira.rest.client.api.RestClientException;\nimport hudson.EnvV"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/pipeline/IssueSelectorStep.java",
    "chars": 3730,
    "preview": "package hudson.plugins.jira.pipeline;\n\nimport com.atlassian.jira.rest.client.api.RestClientException;\nimport edu.umd.cs."
  },
  {
    "path": "src/main/java/hudson/plugins/jira/pipeline/SearchIssuesStep.java",
    "chars": 3399,
    "preview": "package hudson.plugins.jira.pipeline;\n\nimport com.atlassian.jira.rest.client.api.RestClientException;\nimport com.atlassi"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/selector/AbstractIssueSelector.java",
    "chars": 1071,
    "preview": "package hudson.plugins.jira.selector;\n\nimport edu.umd.cs.findbugs.annotations.NonNull;\nimport hudson.ExtensionPoint;\nimp"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/selector/DefaultIssueSelector.java",
    "chars": 7523,
    "preview": "package hudson.plugins.jira.selector;\n\nimport edu.umd.cs.findbugs.annotations.NonNull;\nimport hudson.Extension;\nimport h"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/selector/ExplicitIssueSelector.java",
    "chars": 2269,
    "preview": "package hudson.plugins.jira.selector;\n\nimport edu.umd.cs.findbugs.annotations.CheckForNull;\nimport hudson.EnvVars;\nimpor"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/selector/JqlIssueSelector.java",
    "chars": 2151,
    "preview": "package hudson.plugins.jira.selector;\n\nimport static hudson.Util.fixNull;\n\nimport com.atlassian.jira.rest.client.api.Res"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/selector/perforce/JobIssueSelector.java",
    "chars": 1068,
    "preview": "package hudson.plugins.jira.selector.perforce;\n\nimport hudson.model.Run;\nimport hudson.model.TaskListener;\nimport hudson"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/selector/perforce/P4JobIssueSelector.java",
    "chars": 2457,
    "preview": "package hudson.plugins.jira.selector.perforce;\n\nimport com.perforce.p4java.core.IFix;\nimport hudson.Extension;\nimport hu"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/versionparameter/JiraVersionParameterDefinition.java",
    "chars": 7589,
    "preview": "package hudson.plugins.jira.versionparameter;\n\nimport com.atlassian.jira.rest.client.api.RestClientException;\nimport com"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/versionparameter/JiraVersionParameterValue.java",
    "chars": 1441,
    "preview": "package hudson.plugins.jira.versionparameter;\n\nimport hudson.EnvVars;\nimport hudson.model.AbstractBuild;\nimport hudson.m"
  },
  {
    "path": "src/main/java/hudson/plugins/jira/versionparameter/VersionComparator.java",
    "chars": 996,
    "preview": "package hudson.plugins.jira.versionparameter;\n\nimport com.atlassian.jira.rest.client.api.domain.Version;\nimport java.uti"
  },
  {
    "path": "src/main/resources/atlassian-httpclient-plugin-0.23.0.pom",
    "chars": 8692,
    "preview": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n\n<project xmlns=\"http://maven.apache.org/POM/4.0.0\" xmlns:xsi=\"http://www.w3.org/"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraBuildAction/summary.jelly",
    "chars": 604,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:st=\"jelly:stapler\" xmlns:d=\"jelly:define\" xmlns:l"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateIssueNotifier/config.jelly",
    "chars": 774,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:f=\"/lib/form\">\n    <f:entry title=\"${%Jira Projec"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateIssueNotifier/help-actionIdOnSuccess.html",
    "chars": 195,
    "preview": "<div>\n    <strong>Optional</strong> <br/>\n    The Jira issue status will transition with the configured workflow action "
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateIssueNotifier/help-assignee.html",
    "chars": 118,
    "preview": "<div>\n    <strong>Optional</strong> <br/>\n    This will assign the issue to the given assignee (Jira username).\n</div>"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateIssueNotifier/help-component.html",
    "chars": 301,
    "preview": "<div>\n    <strong>Optional</strong> <br/>\n    Component names that the issue should be assigned to, separated by comma, "
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateIssueNotifier/help-priorityId.html",
    "chars": 130,
    "preview": "<div>\n    <strong>Optional</strong> <br/>\n    This will be the priority of the Jira issue. For project default leave emp"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateIssueNotifier/help-projectKey.html",
    "chars": 101,
    "preview": "<div>\n    <strong>Required</strong> <br/>\n    Specify the projectkey in Uppercase, e.g.: OJRA.\n</div>"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateIssueNotifier/help-testDescription.html",
    "chars": 107,
    "preview": "<div>\n    <strong>Optional</strong> <br/>\n    This will be the description placed in the Jira issue.\n</div>"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateIssueNotifier/help-typeId.html",
    "chars": 110,
    "preview": "<div>\n    <strong>Optional</strong> <br/>\n    This will be the type of the Jira issue, defaults to Bug.\n</div>"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateReleaseNotes/config.jelly",
    "chars": 497,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:f=\"/lib/form\">\n  <f:entry title=\"${%Environment V"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateReleaseNotes/help-jiraEnvironmentVariable.html",
    "chars": 206,
    "preview": "<div>\n    <p>Specify the environment variable to which the release notes will be stored, defaults to RELEASE_NOTES.</p>\n"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateReleaseNotes/help-jiraFilter.html",
    "chars": 196,
    "preview": "<div>\n    <p>Apply additional filtering criteria to the issue filter. This will be concatenated with an AND operator.</p"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateReleaseNotes/help-jiraProjectKey.html",
    "chars": 163,
    "preview": "<div>\n    <p>Specify Jira project key. A project key is the all capitals part before the issue number in Jira.</p>\n    <"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraCreateReleaseNotes/help-jiraRelease.html",
    "chars": 135,
    "preview": "<div>\n    <p>Specify the name of the parameter which will contain the release version. This can reference a build parame"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraEnvironmentVariableBuilder/config.jelly",
    "chars": 251,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:f=\"/lib/form\">\n    <j:if test=\"${descriptor.hasIs"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraEnvironmentVariableBuilder/help.html",
    "chars": 689,
    "preview": "<div>\n  Extracts Jira information for the build to environment variables.\n  <div>Available variables:</div>\n  <ul>\n     "
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraFolderProperty/config.jelly",
    "chars": 294,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:st=\"jelly:stapler\" xmlns:d=\"jelly:define\" xmlns:l"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraGlobalConfiguration/config.jelly",
    "chars": 341,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:st=\"jelly:stapler\" xmlns:d=\"jelly:define\" xmlns:l"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraIssueMigrator/config.jelly",
    "chars": 582,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:f=\"/lib/form\">\n  <f:entry title=\"${%Target Jira R"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraIssueMigrator/help-addRelease.html",
    "chars": 116,
    "preview": "<div>\n    <p>Add Jira Release instead of replace. If checked, Replace Jira Release field will be ignored.</p>\n</div>"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraIssueMigrator/help-jiraProjectKey.html",
    "chars": 154,
    "preview": "<div>\n<p>Specify the project key. A project key is the all capitals part before the issue number in Jira.</p>\n<p>(<stron"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraIssueMigrator/help-jiraQuery.html",
    "chars": 329,
    "preview": "<div>\n    <p>Issues which match this JQL Query will be moved to this release version.</p>\n    <p>This can contain <stron"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraIssueMigrator/help-jiraRelease.html",
    "chars": 135,
    "preview": "<div>\n    <p>Specify the name of the parameter which will contain the release version. This can reference a build parame"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraIssueMigrator/help-jiraReplaceVersion.html",
    "chars": 512,
    "preview": "<div>\n\t<strong>Optional</strong> <br/>\n    <p>If a a value is provided, then only this version will be replaced instead "
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraIssueUpdateBuilder/config.jelly",
    "chars": 929,
    "preview": "<!--\nCopyright 2012 MeetMe, Inc.\n\nLicensed under the Apache License, Version 2.0 (the \"License\");\nyou may not use this f"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraIssueUpdateBuilder/help-comment.html",
    "chars": 235,
    "preview": "<div>\n  An optional comment to be added to the issue after updating the workflow. If left empty, no comment will be adde"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraIssueUpdateBuilder/help-jqlSearch.html",
    "chars": 523,
    "preview": "<div>\n  Issues which match this JQL Query will be progressed using the specified workflow action.\n  <p />\n  This can con"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraIssueUpdateBuilder/help-workflowActionName.html",
    "chars": 363,
    "preview": "<div>\n  The workflow action to be performed on the selected Jira issues.\n  <p />\n  Be mindful of the issues being select"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraIssueUpdateBuilder/help.html",
    "chars": 417,
    "preview": "<div>\n  Performs a Jira workflow action for every issue that matches the JQL query.\n  A common use might be to consider "
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraIssueUpdater/config.jelly",
    "chars": 362,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:st=\"jelly:stapler\" xmlns:d=\"jelly:define\" xmlns:l"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraProjectProperty/config.jelly",
    "chars": 269,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:st=\"jelly:stapler\" xmlns:d=\"jelly:define\" xmlns:l"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraReleaseVersionUpdater/config.jelly",
    "chars": 384,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:f=\"/lib/form\">\n  <f:entry title=\"${%Jira Release}"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraReleaseVersionUpdater/help-jiraDescription.html",
    "chars": 130,
    "preview": "<div>\n\t<strong>Optional</strong> <br/>\n\tSpecify a description of the release version. This can reference a build paramet"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraReleaseVersionUpdater/help-jiraProjectKey.html",
    "chars": 154,
    "preview": "<div>\n<p>Specify the project key. A project key is the all capitals part before the issue number in Jira.</p>\n<p>(<stron"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraReleaseVersionUpdater/help-jiraRelease.html",
    "chars": 124,
    "preview": "<div>\nSpecify the name of the parameter which will contain the release version. This can reference a build parameter.\n</"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraReleaseVersionUpdaterBuilder/config.jelly",
    "chars": 388,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:f=\"/lib/form\">\n  <f:entry title=\"${%Jira Release}"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraReleaseVersionUpdaterBuilder/help-jiraDescription.html",
    "chars": 130,
    "preview": "<div>\n\t<strong>Optional</strong> <br/>\n\tSpecify a description of the release version. This can reference a build paramet"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraReleaseVersionUpdaterBuilder/help-jiraProjectKey.html",
    "chars": 154,
    "preview": "<div>\n<p>Specify the project key. A project key is the all capitals part before the issue number in Jira.</p>\n<p>(<stron"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraReleaseVersionUpdaterBuilder/help-jiraRelease.html",
    "chars": 124,
    "preview": "<div>\nSpecify the name of the parameter which will contain the release version. This can reference a build parameter.\n</"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/config.jelly",
    "chars": 2640,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:st=\"jelly:stapler\" xmlns:d=\"jelly:define\" xmlns:l"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/config.properties",
    "chars": 181,
    "preview": "site.alternativeUrl=Jira alternative URL\nsite.timeout=in seconds\nsite.useBearerAuth=Note: Bearer authentication is only "
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/config_de.properties",
    "chars": 77,
    "preview": "Jira\\ sites=Jira Instanzen\nSupports\\ Wiki\\ notation=Untersttzt Wiki-Notation\n"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/config_fr.properties",
    "chars": 140,
    "preview": "Jira\\ sites=Sites Jira\nSupports\\ Wiki\\ notation= Support des annotations wiki.\nRecord\\ Scm\\ changes= Enregistrement des "
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/config_it.properties",
    "chars": 215,
    "preview": "site.alternativeUrl=URL alternativo di Jira\nsite.timeout=in secondi\nsite.useBearerAuth=Nota: L'autenticazione del portat"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/config_ja.properties",
    "chars": 389,
    "preview": "Jira\\ sites=Jira \\u30B5\\u30A4\\u30C8\nSupports\\ Wiki\\ notation=Wiki\\u8A18\\u6CD5\\u306E\\u30B5\\u30DD\\u30FC\\u30C8\nRecord\\ Scm\\"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/config_nl.properties",
    "chars": 1249,
    "preview": "# The MIT License\n#\n# Copyright (c) 2004-2010, Sun Microsystems, Inc.\n#\n# Permission is hereby granted, free of charge, "
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/config_pl.properties",
    "chars": 227,
    "preview": "site.alternativeUrl=Alternatywny Jira URL\nsite.timeout=w sekundach\nsite.useBearerAuth=Uwaga: uwierzytelnianie Bearer jes"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-alternativeUrl.html",
    "chars": 140,
    "preview": "<div>\n  Specify the root URL of your Jira installation for &quot;normal&quot; access, like <tt>https://issues.apache.org"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-appendChangeTimestamp.html",
    "chars": 87,
    "preview": "<div>\n  If activated, SCM change entries date and time will be recorded in Jira.\n</div>"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-credentialsId.html",
    "chars": 344,
    "preview": "<div>\n  If the remote API support is enabled in this Jira, you can set\n  a valid account information. This would allow p"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-credentialsId_de.html",
    "chars": 345,
    "preview": "<div>\n  Falls die Remote-API Unterstützung in Jira aktiviert ist, kann man hier\n  die Login-Informationen angeben. Damit"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-credentialsId_fr.html",
    "chars": 394,
    "preview": "<div>\n  Si l'api \"remote\" est activ&#233; dans Jira, vous pouvez configurer un compte valide.\n  Cel&#224; permettra aux "
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-credentialsId_ja.html",
    "chars": 143,
    "preview": "<div>\n  JiraでリモートAPIがサポートされている場合、正しいアカウント情報を設定します。\n  設定すると、ビルドが変更を統合した際にissueを更新します。\n  また、プロジェクトの設定画面で、どのJiraを更新するか選択するこ"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-dateTimePattern.html",
    "chars": 209,
    "preview": "<div>\nSee <a href=\"https://docs.oracle.com/javase/7/docs/api/java/text/SimpleDateFormat.html\">javadoc</a> for SimpleDate"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-disableChangelogAnnotations.html",
    "chars": 68,
    "preview": "<div>\n    Disable creating Jira hyperlinks in the changeset.\n</div>\n"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-groupVisibility.html",
    "chars": 171,
    "preview": "<div>\n  Enter the name of the Jira group that has permission to view\n  the comment, leave the field empty to make the co"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-maxIssuesFromJqlSearch.html",
    "chars": 192,
    "preview": "<div>\nSpecifies the maximum number of issues to load from the JQL search query. If this number exceeds the limit configu"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-readTimeout.html",
    "chars": 64,
    "preview": "<div>\nRead timeout for Jira REST API calls (in seconds).\n</div>\n"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-recordScmChanges.html",
    "chars": 122,
    "preview": "<div>\n  If activated, scm changes will be recorded in Jira : link to the scm repository browser and paths changes.\n</div"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-recordScmChanges_fr.html",
    "chars": 156,
    "preview": "<div>\n  Si activ&#233;, les changements du scm seront enregistr&#233;s dans Jira : avec un lien vers le \"browser\" de scm"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-recordScmChanges_ja.html",
    "chars": 62,
    "preview": "<div>\n  SCMリポジトリブラウザへのリンクやパスの変更が、SCMが変更されるとJiraに記録されます。\n</div>"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-roleVisibility.html",
    "chars": 178,
    "preview": "<div>\n  Enter the name of the Jira project role that has permission to view\n  the comment, leave the field empty to make"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-supportsWikiStyleComment.html",
    "chars": 230,
    "preview": "<div>\n  Check this box if this Jira supports Wiki notations in comments.\n  When checked, Jenkins will post comments that"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-supportsWikiStyleComment_de.html",
    "chars": 220,
    "preview": "<div>\r\n  Aktivieren Sie diese Checkbox, falls die Jira Instanz Wiki-Notation unterstützt.\r\n  Falls aktiv, wird Jenkins K"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-supportsWikiStyleComment_fr.html",
    "chars": 238,
    "preview": "<div>\n  Cochez si votre Jira supporte la syntaxe WIKI dans les commentaires.\n  Si activ&#233;, Jenkins postera des comme"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-supportsWikiStyleComment_ja.html",
    "chars": 157,
    "preview": "<div>\n  このJiraがコメントの記述にWiki記法をサポートしているなら、このチェックボックスをチェックしてください。\n  チェックすると、JenkinsはWiki記法を使用してコメントをポストします。\n  チェックしないと、Jen"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-threadExecutorNumber.html",
    "chars": 173,
    "preview": "<div>\nSize of the Thread Pool Executor to query Jira.\n<b>If you have a lot of builds using the Jira plugin, it might be "
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-timeout.html",
    "chars": 70,
    "preview": "<div>\nConnection timeout for Jira REST API calls (in seconds).\n</div>\n"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-updateJiraIssueForAllStatus.html",
    "chars": 220,
    "preview": "<div>\n    <p>If this is unchecked, issues will be only updated if the build is SUCCESSful or UNSTABLE.</p>\n    <p>If thi"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-url.html",
    "chars": 109,
    "preview": "<div>\n  Specify the root URL of your Jira installation, like <tt>http://issues.apache.org/jira/</tt>.\n</div>\n"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-url_de.html",
    "chars": 103,
    "preview": "<div>\n  Geben Sie die Root-URL der Jira Instanz an, z.B. <tt>http://issues.apache.org/jira/</tt>\n</div>"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-url_fr.html",
    "chars": 103,
    "preview": "<div>\n  URL racine de votre installation Jira, exemple : <tt>http://issues.apache.org/jira/</tt>\n</div>"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-url_ja.html",
    "chars": 81,
    "preview": "<div>\n  <tt>http://issues.apache.org/jira/</tt> のように、JiraのルートURLを指定してください。\n</div>"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-useHTTPAuth.html",
    "chars": 480,
    "preview": "<div>\n  This option forces Jenkins to connect to Jira using HTTP Basic Authentication, instead of logging in\n  over RPC."
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-userPattern.html",
    "chars": 306,
    "preview": "<div>\n  You can define your own pattern to search for Jira issue ids in the SCM logs.<br />\n  If empty the default one i"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-userPattern_de.html",
    "chars": 331,
    "preview": "<div>\n  Eigenes Suchmuster (regulärer Ausdruck) zum Erkennen von Jira IssueS definieren.<br />\n  Falls leer, wird das St"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-userPattern_fr.html",
    "chars": 251,
    "preview": "<div>\n  Vous pouvez d&#233;finir ici votre pattern pour rechercher les Ids Jira dans les commentaires\n   du commit dans "
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraSite/help-userPattern_ja.html",
    "chars": 148,
    "preview": "<div>\n  SCMのログからJiraの課題IDを検索するパターンを定義することができます。\n  設定しないとデフォルトのパターン ([a-zA-Z][a-zA-Z0-9_]+-[1-9][0-9]*)([^.]|\\.[^0-9]|\\.$"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraVersionCreator/config.jelly",
    "chars": 418,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:f=\"/lib/form\">\n  <f:entry title=\"${%Jira Version}"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraVersionCreator/help-failIfAlreadyExists.html",
    "chars": 193,
    "preview": "<div>\n    When checked (default), the build will fail if the version already exists in Jira. \n    When unchecked, the bu"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraVersionCreator/help-jiraProjectKey.html",
    "chars": 154,
    "preview": "<div>\n<p>Specify the project key. A project key is the all capitals part before the issue number in Jira.</p>\n<p>(<stron"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraVersionCreator/help-jiraVersion.html",
    "chars": 124,
    "preview": "<div>\nSpecify the name of the parameter which will contain the release version. This can reference a build parameter.\n</"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraVersionCreatorBuilder/config.jelly",
    "chars": 418,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" xmlns:f=\"/lib/form\">\n  <f:entry title=\"${%Jira Version}"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraVersionCreatorBuilder/help-failIfAlreadyExists.html",
    "chars": 193,
    "preview": "<div>\n    When checked (default), the build will fail if the version already exists in Jira. \n    When unchecked, the bu"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraVersionCreatorBuilder/help-jiraProjectKey.html",
    "chars": 154,
    "preview": "<div>\n<p>Specify the project key. A project key is the all capitals part before the issue number in Jira.</p>\n<p>(<stron"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/JiraVersionCreatorBuilder/help-jiraVersion.html",
    "chars": 124,
    "preview": "<div>\nSpecify the name of the parameter which will contain the release version. This can reference a build parameter.\n</"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/MavenJiraIssueUpdater/config.jelly",
    "chars": 67,
    "preview": "<?jelly escape-by-default='true'?>\n<j:jelly xmlns:j=\"jelly:core\" />"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/Messages.properties",
    "chars": 4007,
    "preview": "JiraIssueUpdater.DisplayName=Jira: Update relevant issues\nJiraFolderProperty.DisplayName=Associated Jira\nJiraProjectProp"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/Messages_de.properties",
    "chars": 642,
    "preview": "JiraProjectProperty.DisplayName=Zugeh\\u00f6rige Jira-Instanz\nJiraProjectProperty.JiraUrlMandatory=Jira URL ist ein Pflic"
  },
  {
    "path": "src/main/resources/hudson/plugins/jira/Messages_fr.properties",
    "chars": 4359,
    "preview": "JiraIssueUpdater.DisplayName=Jira : Mise \\u00e0 jour des demandes\nJiraProjectProperty.DisplayName=Jira associ\\u00e9\nJira"
  }
]

// ... and 100 more files (download for full content)

About this extraction

This page contains the full source code of the jenkinsci/jira-plugin GitHub repository, extracted and formatted as plain text for AI agents and large language models (LLMs). The extraction includes 300 files (775.0 KB), approximately 183.7k tokens, and a symbol index with 1297 extracted functions, classes, methods, constants, and types. Use this with OpenClaw, Claude, ChatGPT, Cursor, Windsurf, or any other AI tool that accepts text input. You can copy the full output to your clipboard or download it as a .txt file.

Extracted by GitExtract — free GitHub repo to text converter for AI. Built by Nikandr Surkov.

Copied to clipboard!