-
Notifications
You must be signed in to change notification settings - Fork 107
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
jep-227 downstream usage #357
Merged
Merged
Changes from all commits
Commits
Show all changes
2 commits
Select commit
Hold shift + click to select a range
File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -52,7 +52,7 @@ | |
import hudson.model.ModelObject; | ||
import hudson.security.ACL; | ||
import hudson.security.ACLContext; | ||
import hudson.security.AccessDeniedException2; | ||
import hudson.security.AccessDeniedException3; | ||
import hudson.security.Permission; | ||
import hudson.util.CopyOnWriteMap; | ||
import hudson.util.ListBoxModel; | ||
|
@@ -69,11 +69,11 @@ | |
import jenkins.model.Jenkins; | ||
import net.jcip.annotations.GuardedBy; | ||
import net.sf.json.JSONObject; | ||
import org.acegisecurity.Authentication; | ||
import org.kohsuke.accmod.Restricted; | ||
import org.kohsuke.accmod.restrictions.NoExternalUse; | ||
import org.kohsuke.stapler.DataBoundConstructor; | ||
import org.kohsuke.stapler.StaplerRequest; | ||
import org.springframework.security.core.Authentication; | ||
|
||
/** | ||
* A store of credentials that can be used as a Stapler object. | ||
|
@@ -102,27 +102,14 @@ | |
return super.getScopes(object); | ||
} | ||
|
||
/** | ||
* {@inheritDoc} | ||
*/ | ||
@NonNull | ||
@Override | ||
public <C extends Credentials> List<C> getCredentials(@NonNull Class<C> type, @Nullable ItemGroup itemGroup, | ||
@Nullable Authentication authentication) { | ||
return getCredentials(type, itemGroup, authentication, Collections.emptyList()); | ||
} | ||
|
||
/** | ||
* {@inheritDoc} | ||
*/ | ||
@NonNull | ||
@Override | ||
public <C extends Credentials> List<C> getCredentials(@NonNull Class<C> type, @Nullable ItemGroup itemGroup, | ||
public <C extends Credentials> List<C> getCredentialsInItemGroup(@NonNull Class<C> type, @Nullable ItemGroup itemGroup, | ||
@Nullable Authentication authentication, | ||
@NonNull List<DomainRequirement> domainRequirements) { | ||
List<C> result = new ArrayList<>(); | ||
Set<String> ids = new HashSet<>(); | ||
if (ACL.SYSTEM.equals(authentication)) { | ||
if (ACL.SYSTEM2.equals(authentication)) { | ||
while (itemGroup != null) { | ||
if (itemGroup instanceof AbstractFolder) { | ||
final AbstractFolder<?> folder = AbstractFolder.class.cast(itemGroup); | ||
|
@@ -156,29 +143,29 @@ | |
*/ | ||
@NonNull | ||
@Override | ||
public <C extends Credentials> List<C> getCredentials(@NonNull Class<C> type, @NonNull Item item, | ||
public <C extends Credentials> List<C> getCredentialsInItem(@NonNull Class<C> type, @NonNull Item item, | ||
@Nullable Authentication authentication, | ||
@NonNull List<DomainRequirement> domainRequirements) { | ||
if (item instanceof AbstractFolder) { | ||
// credentials defined in the folder should be available in the context of the folder | ||
return getCredentials(type, (ItemGroup) item, authentication, domainRequirements); | ||
return getCredentialsInItemGroup(type, (ItemGroup) item, authentication, domainRequirements); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. clearer 👍 |
||
} | ||
return super.getCredentials(type, item, authentication, domainRequirements); | ||
return super.getCredentialsInItem(type, item, authentication, domainRequirements); | ||
} | ||
|
||
/** | ||
* {@inheritDoc} | ||
*/ | ||
@NonNull | ||
@Override | ||
public <C extends IdCredentials> ListBoxModel getCredentialIds(@NonNull Class<C> type, | ||
public <C extends IdCredentials> ListBoxModel getCredentialIdsInItemGroup(@NonNull Class<C> type, | ||
@Nullable ItemGroup itemGroup, | ||
@Nullable Authentication authentication, | ||
@NonNull List<DomainRequirement> domainRequirements, | ||
@NonNull CredentialsMatcher matcher) { | ||
ListBoxModel result = new ListBoxModel(); | ||
Set<String> ids = new HashSet<>(); | ||
if (ACL.SYSTEM.equals(authentication)) { | ||
if (ACL.SYSTEM2.equals(authentication)) { | ||
while (itemGroup != null) { | ||
if (itemGroup instanceof AbstractFolder) { | ||
final AbstractFolder<?> folder = AbstractFolder.class.cast(itemGroup); | ||
|
@@ -210,189 +197,189 @@ | |
*/ | ||
@NonNull | ||
@Override | ||
public <C extends IdCredentials> ListBoxModel getCredentialIds(@NonNull Class<C> type, @NonNull Item item, | ||
public <C extends IdCredentials> ListBoxModel getCredentialIdsInItem(@NonNull Class<C> type, @NonNull Item item, | ||
@Nullable Authentication authentication, | ||
@NonNull List<DomainRequirement> domainRequirements, | ||
@NonNull CredentialsMatcher matcher) { | ||
if (item instanceof AbstractFolder) { | ||
// credentials defined in the folder should be available in the context of the folder | ||
return getCredentialIds(type, (ItemGroup) item, authentication, domainRequirements, matcher); | ||
return getCredentialIdsInItemGroup(type, (ItemGroup) item, authentication, domainRequirements, matcher); | ||
} | ||
return getCredentialIds(type, item.getParent(), authentication, domainRequirements, matcher); | ||
return getCredentialIdsInItemGroup(type, item.getParent(), authentication, domainRequirements, matcher); | ||
} | ||
|
||
/** | ||
* {@inheritDoc} | ||
*/ | ||
@Override | ||
public CredentialsStore getStore(@CheckForNull ModelObject object) { | ||
if (object instanceof AbstractFolder) { | ||
final AbstractFolder<?> folder = AbstractFolder.class.cast(object); | ||
FolderCredentialsProperty property = folder.getProperties().get(FolderCredentialsProperty.class); | ||
if (property != null) { | ||
return property.getStore(); | ||
} | ||
synchronized (emptyProperties) { | ||
property = emptyProperties.get(folder); | ||
if (property == null) { | ||
property = new FolderCredentialsProperty(folder); | ||
emptyProperties.put(folder, property); | ||
} | ||
} | ||
return property.getStore(); | ||
} | ||
return null; | ||
} | ||
|
||
/** | ||
* {@inheritDoc} | ||
*/ | ||
@Override | ||
public String getIconClassName() { | ||
return "icon-folder-store"; | ||
} | ||
|
||
/** | ||
* Our property. | ||
*/ | ||
public static class FolderCredentialsProperty extends AbstractFolderProperty<AbstractFolder<?>> { | ||
|
||
/** | ||
* Old store of credentials | ||
* | ||
* @deprecated | ||
*/ | ||
@Deprecated | ||
private transient List<Credentials> credentials; | ||
|
||
/** | ||
* Our credentials. | ||
* | ||
* @since 3.10 | ||
*/ | ||
private Map<Domain, List<Credentials>> domainCredentialsMap = | ||
new CopyOnWriteMap.Hash<>(); | ||
|
||
/** | ||
* Our store. | ||
*/ | ||
private transient StoreImpl store = new StoreImpl(); | ||
|
||
/*package*/ FolderCredentialsProperty(AbstractFolder<?> owner) { | ||
setOwner(owner); | ||
domainCredentialsMap = DomainCredentials.migrateListToMap(null, null); | ||
} | ||
|
||
/** | ||
* Backwards compatibility. | ||
* | ||
* @param credentials the credentials. | ||
* @deprecated | ||
*/ | ||
@Deprecated | ||
public FolderCredentialsProperty(List<Credentials> credentials) { | ||
domainCredentialsMap = DomainCredentials.migrateListToMap(domainCredentialsMap, credentials); | ||
} | ||
|
||
/** | ||
* Constructor for stapler. | ||
* | ||
* @param domainCredentials the credentials. | ||
* @since 1.5 | ||
*/ | ||
@DataBoundConstructor | ||
public FolderCredentialsProperty(DomainCredentials[] domainCredentials) { | ||
domainCredentialsMap = DomainCredentials.asMap(Arrays.asList(domainCredentials)); | ||
} | ||
|
||
/** | ||
* Resolve old data store into new data store. | ||
* | ||
* @since 1.5 | ||
*/ | ||
@SuppressFBWarnings(value = "IS2_INCONSISTENT_SYNC", justification = "Only unprotected during deserialization") | ||
@SuppressWarnings("deprecation") | ||
private Object readResolve() throws ObjectStreamException { | ||
if (domainCredentialsMap == null) { | ||
domainCredentialsMap = DomainCredentials.migrateListToMap(domainCredentialsMap, credentials); | ||
credentials = null; | ||
} | ||
return this; | ||
} | ||
|
||
public <C extends Credentials> List<C> getCredentials(Class<C> type) { | ||
List<C> result = new ArrayList<>(); | ||
for (Credentials credential : getCredentials()) { | ||
if (type.isInstance(credential)) { | ||
result.add(type.cast(credential)); | ||
} | ||
} | ||
return result; | ||
} | ||
|
||
/** | ||
* Gets all the folder's credentials. | ||
* | ||
* @return all the folder's credentials. | ||
*/ | ||
@SuppressWarnings("unused") // used by stapler | ||
public List<Credentials> getCredentials() { | ||
return getDomainCredentialsMap().get(Domain.global()); | ||
} | ||
|
||
/** | ||
* Returns the {@link com.cloudbees.plugins.credentials.domains.DomainCredentials} | ||
* | ||
* @return the {@link com.cloudbees.plugins.credentials.domains.DomainCredentials} | ||
* @since 3.10 | ||
*/ | ||
@SuppressWarnings("unused") // used by stapler | ||
public List<DomainCredentials> getDomainCredentials() { | ||
return DomainCredentials.asList(getDomainCredentialsMap()); | ||
} | ||
|
||
/** | ||
* The Map of domain credentials. | ||
* | ||
* @return The Map of domain credentials. | ||
* @since 3.10 | ||
*/ | ||
@SuppressWarnings("deprecation") | ||
@NonNull | ||
public synchronized Map<Domain, List<Credentials>> getDomainCredentialsMap() { | ||
return domainCredentialsMap = DomainCredentials.migrateListToMap(domainCredentialsMap, credentials); | ||
} | ||
|
||
/** | ||
* Sets the map of domain credentials. | ||
* | ||
* @param domainCredentialsMap the map of domain credentials. | ||
* @since 3.10 | ||
*/ | ||
public synchronized void setDomainCredentialsMap(Map<Domain, List<Credentials>> domainCredentialsMap) { | ||
this.domainCredentialsMap = DomainCredentials.toCopyOnWriteMap(domainCredentialsMap); | ||
} | ||
|
||
/** | ||
* Returns the {@link StoreImpl}. | ||
* @return the {@link StoreImpl}. | ||
*/ | ||
@NonNull | ||
public synchronized StoreImpl getStore() { | ||
if (store == null) { | ||
store = new StoreImpl(); | ||
} | ||
return store; | ||
} | ||
|
||
/** | ||
* Short-cut method for checking {@link CredentialsStore#hasPermission(hudson.security.Permission)} | ||
* | ||
* @param p the permission to check. | ||
*/ | ||
private void checkPermission(Permission p) { | ||
if (!store.hasPermission(p)) { | ||
throw new AccessDeniedException2(Jenkins.getAuthentication(), p); | ||
throw new AccessDeniedException3(Jenkins.getAuthentication2(), p); | ||
} | ||
} | ||
|
||
|
@@ -405,7 +392,7 @@ | |
*/ | ||
private void checkedSave(Permission p) throws IOException { | ||
checkPermission(p); | ||
try (ACLContext oldContext = ACL.as(ACL.SYSTEM)) { | ||
try (ACLContext oldContext = ACL.as2(ACL.SYSTEM2)) { | ||
FolderCredentialsProperty property = | ||
owner.getProperties().get(FolderCredentialsProperty.class); | ||
if (property == null) { | ||
|
@@ -651,8 +638,8 @@ | |
* {@inheritDoc} | ||
*/ | ||
@Override | ||
public boolean hasPermission(@NonNull Authentication a, @NonNull Permission permission) { | ||
return owner.getACL().hasPermission(a, permission); | ||
public boolean hasPermission2(@NonNull Authentication a, @NonNull Permission permission) { | ||
return owner.getACL().hasPermission2(a, permission); | ||
} | ||
|
||
/** | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -41,7 +41,6 @@ | |
import hudson.model.FreeStyleBuild; | ||
import hudson.model.FreeStyleProject; | ||
import hudson.model.Item; | ||
import hudson.model.ItemGroup; | ||
import hudson.model.Result; | ||
import hudson.model.User; | ||
import hudson.security.ACL; | ||
|
@@ -83,21 +82,21 @@ public void foldersHaveTheirOwnStore() throws Exception { | |
public void credentialsAvailableAtFolderScope() throws Exception { | ||
Folder f = createFolder(); | ||
List<StandardUsernamePasswordCredentials> asGroup = | ||
CredentialsProvider.lookupCredentials(StandardUsernamePasswordCredentials.class, (ItemGroup) f, | ||
ACL.SYSTEM, Collections.emptyList()); | ||
CredentialsProvider.lookupCredentialsInItemGroup(StandardUsernamePasswordCredentials.class, f, | ||
Comment on lines
-86
to
+85
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. no cast needed for method resolution 👍 |
||
ACL.SYSTEM2, Collections.emptyList()); | ||
List<StandardUsernamePasswordCredentials> asItem = | ||
CredentialsProvider.lookupCredentials(StandardUsernamePasswordCredentials.class, (Item) f, | ||
ACL.SYSTEM, Collections.emptyList()); | ||
CredentialsProvider.lookupCredentialsInItem(StandardUsernamePasswordCredentials.class, f, | ||
ACL.SYSTEM2, Collections.emptyList()); | ||
assertThat(asGroup, is(asItem)); | ||
CredentialsStore folderStore = getFolderStore(f); | ||
UsernamePasswordCredentialsImpl credentials = | ||
new UsernamePasswordCredentialsImpl(CredentialsScope.GLOBAL, "test-id", "description", "test-user", | ||
"secret"); | ||
folderStore.addCredentials(Domain.global(), credentials); | ||
asGroup = CredentialsProvider.lookupCredentials(StandardUsernamePasswordCredentials.class, (ItemGroup) f, | ||
ACL.SYSTEM, Collections.emptyList()); | ||
asItem = CredentialsProvider.lookupCredentials(StandardUsernamePasswordCredentials.class, (Item) f, | ||
ACL.SYSTEM, Collections.emptyList()); | ||
asGroup = CredentialsProvider.lookupCredentialsInItemGroup(StandardUsernamePasswordCredentials.class, f, | ||
ACL.SYSTEM2, Collections.emptyList()); | ||
asItem = CredentialsProvider.lookupCredentialsInItem(StandardUsernamePasswordCredentials.class, f, | ||
ACL.SYSTEM2, Collections.emptyList()); | ||
assertThat(asGroup, is(asItem)); | ||
assertThat(asGroup, hasItem(credentials)); | ||
assertThat(asItem, hasItem(credentials)); | ||
|
@@ -107,11 +106,11 @@ public void credentialsAvailableAtFolderScope() throws Exception { | |
public void credentialsListableAtFolderScope() throws Exception { | ||
Folder f = createFolder(); | ||
ListBoxModel asGroup = | ||
CredentialsProvider.listCredentials(StandardUsernamePasswordCredentials.class, (ItemGroup) f, | ||
ACL.SYSTEM, Collections.emptyList(), CredentialsMatchers.always()); | ||
CredentialsProvider.listCredentialsInItemGroup(StandardUsernamePasswordCredentials.class, f, | ||
ACL.SYSTEM2, Collections.emptyList(), CredentialsMatchers.always()); | ||
ListBoxModel asItem = | ||
CredentialsProvider.listCredentials(StandardUsernamePasswordCredentials.class, (Item) f, | ||
ACL.SYSTEM, Collections.emptyList(), CredentialsMatchers.always()); | ||
CredentialsProvider.listCredentialsInItem(StandardUsernamePasswordCredentials.class, f, | ||
ACL.SYSTEM2, Collections.emptyList(), CredentialsMatchers.always()); | ||
assertThat(asGroup, is(asItem)); | ||
assertThat(asGroup.size(), is(0)); | ||
assertThat(asItem.size(), is(0)); | ||
|
@@ -120,10 +119,10 @@ public void credentialsListableAtFolderScope() throws Exception { | |
new UsernamePasswordCredentialsImpl(CredentialsScope.GLOBAL, "test-id", "description", "test-user", | ||
"secret"); | ||
folderStore.addCredentials(Domain.global(), credentials); | ||
asGroup = CredentialsProvider.listCredentials(StandardUsernamePasswordCredentials.class, (ItemGroup) f, | ||
ACL.SYSTEM, Collections.emptyList(), CredentialsMatchers.always()); | ||
asItem = CredentialsProvider.listCredentials(StandardUsernamePasswordCredentials.class, (Item) f, | ||
ACL.SYSTEM, Collections.emptyList(), CredentialsMatchers.always()); | ||
asGroup = CredentialsProvider.listCredentialsInItemGroup(StandardUsernamePasswordCredentials.class, f, | ||
ACL.SYSTEM2, Collections.emptyList(), CredentialsMatchers.always()); | ||
asItem = CredentialsProvider.listCredentialsInItem(StandardUsernamePasswordCredentials.class, f, | ||
ACL.SYSTEM2, Collections.emptyList(), CredentialsMatchers.always()); | ||
assertThat(asGroup.size(), is(1)); | ||
assertThat(asGroup.get(0).value, is("test-id")); | ||
assertThat(asItem.size(), is(1)); | ||
|
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fewer overloads to deal with 👍