@PublicApi
public interface StructureManager
StructureManager
is the main component used to manage structures as entities.
To access and manage structure contents - its forest
, a hierarchical list of items, -
see ForestService
.
A Structure
is a named entity that has properties like name, description and permissions.
Methods in this interface allow creating/removing structures and changing those properties.
Unless otherwise stated, all methods are thread-safe.
Note that the methods of the Structure
interface are not thread-safe - you need
to retrieve a separate instance in every thread where you need it.
All methods that return Structure
instances return new independent instances every time they are
called.
All methods check permissions for the current user as returned by StructureAuth.getUser()
, unless
permission checking is turned off by setting StructureAuth.isSecurityOverridden()
flag
(useful if you are writing an administrative task - see StructureAuth.sudo(ApplicationUser, boolean, CallableE)
).
Creating a structure:
Structure newStructure = structureManager.createStructure().setName("structureName").saveChanges();
Changing a structure:
List<Structure> structures = structureManager.getStructuresByName("hideme", ADMIN); for (Structure s : structures) { s.setPermissions(Collections.emptyList()).saveChanges(); }
Structure
,
Forest
,
ForestService
Modifier and Type | Method and Description |
---|---|
void |
addListener(StructureListener listener)
Adds a structure listener.
|
Structure |
copyStructure(Long structureId,
ApplicationUser newOwner,
boolean copyPermissions)
Copies the structure and the forest it contains into a new structure.
|
Structure |
copyStructureWithoutForest(Long structureId,
ApplicationUser newOwner,
boolean copyPermissions)
Copies the structure into a new structure - only the properties (such as name, description, permissions)
are copied, not the forest.
|
Structure |
createStructure()
Creates an empty new structure.
|
void |
deleteStructure(Long id)
Deletes the specified structure and its content.
|
List<Structure> |
getAllStructures(PermissionLevel requiredLevel)
Retrieves a list of all unarchived structures that are accessible to the
current user at the specified permission level.
|
List<Structure> |
getAllStructures(PermissionLevel requiredLevel,
boolean includeArchived)
Retrieves a list of all structures that are visible to the current user
at the specified permission level.
|
List<Structure> |
getArchivedStructures(PermissionLevel requiredLevel)
Retrieves a list of all archived structures that are visible to the current user
at the specified permission level.
|
Long |
getSingleViewableStructureId()
Convenience method that returns the ID of a single structure that the
current user can see.
|
Structure |
getStructure(Long structureId,
PermissionLevel requiredLevel)
Retrieves a structure given structure ID.
|
PermissionLevel |
getStructurePermission(Long structureId)
Calculates access level to a structure for the current user.
|
PermissionLevel |
getStructurePermission(Long structureId,
ApplicationUser user)
Calculates access level to a structure for the specified user.
|
List<Structure> |
getStructuresByName(String name,
PermissionLevel requiredLevel)
Convenience method to search for unarchived structures with the specified name.
|
List<Structure> |
getStructuresByName(String name,
PermissionLevel requiredLevel,
boolean searchArchivedStructures)
Convenience method that searches for structures with the specified name.
|
List<Structure> |
getStructuresOwnedBy(ApplicationUser user)
Retrieves a list of all structures visible to the current user,
for which the specified user is the owner.
|
List<Structure> |
getViewableStructuresWithIssue(Long issueId)
Retrieves all structures that contain the specified issue.
|
boolean |
hasNonArchivedStructuresForUser()
Convenience method that checks whether the current user can see at least one
unarchived structure.
|
boolean |
isAccessible(Long structureId,
PermissionLevel requiredLevel)
Checks that the specified structure exists and the current user has access to it
with the required permission level.
|
boolean |
isEffectorConfigurationAllowed(Long structureId,
ApplicationUser user)
Checks that the specified user has the
CONFIGURE_EFFECTORS
app permission and has at least AUTOMATE
access level to the specified structure. |
boolean |
isEffectorExecutionAllowed(Long structureId,
ApplicationUser user)
Checks that the specified user has the
EXECUTE_EFFECTORS
app permission and has at least VIEW
access level to the specified structure. |
boolean |
isGeneratorConfigurationAllowed(Long structureId,
ApplicationUser user)
Checks that the specified user has the
CONFIGURE_GENERATORS
app permission and has at least AUTOMATE
access level to the specified structure. |
boolean |
isIssueInStructureNoAccessCheck(Long issueId,
Long structureId)
Checks if a specific issue (not row!) belongs to a specific structure.
|
void |
removeListener(StructureListener listener)
Removes the listener previously added via
addListener(StructureListener) . |
@NotNull Structure getStructure(@Nullable Long structureId, @Nullable PermissionLevel requiredLevel) throws StructureException
Retrieves a structure given structure ID. Throws exception if the structure does not exist or is not accessible.
The second parameter allows to specify the required permission level for the current user.
Unless StructureAuth.isSecurityOverridden()
is true, we also check if the user
has access to Structure plugin.
Every call to getStructure()
will return a new instance of Structure
, which will contain
a snapshot of the structure's properties. You shouldn't keep that instance around for long, because any
changes to the structure, made by other code in parallel, will not be reflected in this snapshot instance.
structureId
- the ID of the structure, nullable for convenience (if null, will throw StructureException)requiredLevel
- when checking for user's permission, require that the user has at least the specified permission.
Passing null of PermissionLevel.NONE
effectively disables the structure permissions check, but we still
check that the user has access to Structure plugin (unless StructureAuth.isSecurityOverridden()
is true).StructureException
- if structure is not found, or the user is not allowed to use Structure,
or the user does not have the required access level to this structure, or if any other problem is encountered@NotNull List<Structure> getAllStructures(@Nullable PermissionLevel requiredLevel)
Retrieves a list of all unarchived structures that are accessible to the current user at the specified permission level.
The method scans all existing structures, selects unarchived ones and checks permissions.
If the user has no access to Structure plugin, returns empty list.
If StructureAuth.isSecurityOverridden()
is true, ignores all of the checks above and
returns all unarchived structures.
The resulting list is sorted by name, using the current user's locale.
requiredLevel
- when checking for user's permission, require that the user
has at least the specified permission for every structure in the returned list.
Passing null of PermissionLevel.NONE
effectively disables the structure permissions check, but we still
check that the user has access to Structure plugin (unless StructureAuth.isSecurityOverridden()
is true).getAllStructures(PermissionLevel, boolean)
@NotNull List<Structure> getAllStructures(@Nullable PermissionLevel requiredLevel, boolean includeArchived)
Retrieves a list of all structures that are visible to the current user at the specified permission level.
The method scans all existing structures and checks permissions.
If the user has no access to Structure plugin, returns empty list.
If StructureAuth.isSecurityOverridden()
is true, ignores all of the checks above and returns all structures
(or only unarchived, depending on the parameter).
The resulting list is sorted by name, using the current user's locale.
requiredLevel
- when checking for user's permission, require that the user
has at least the specified permission for every structure in the returned list.
Passing null of PermissionLevel.NONE
effectively disables the structure permissions check, but we still
check that the user has access to Structure plugin (unless StructureAuth.isSecurityOverridden()
is true).includeArchived
- if true, result will also contain archived structures@NotNull List<Structure> getArchivedStructures(@Nullable PermissionLevel requiredLevel)
Retrieves a list of all archived structures that are visible to the current user at the specified permission level.
The method scans all existing structures, selects archived ones and checks permissions.
If the user has no access to Structure plugin, returns empty list.
If StructureAuth.isSecurityOverridden()
is true, ignores all of the checks above and
returns all archived structures.
The resulting list is sorted by name, using the current user's locale.
requiredLevel
- when checking for user's permission, require that the user
has at least the specified permission for every structure in the returned list.
Passing null of PermissionLevel.NONE
effectively disables the structure permissions check, but we still
check that the user has access to Structure plugin (unless StructureAuth.isSecurityOverridden()
is true).@NotNull List<Structure> getStructuresOwnedBy(@Nullable ApplicationUser user)
Retrieves a list of all structures visible to the current user, for which the specified user is the owner.
The method scans all existing structures and looks for those that are
owned by the specified user and visible to the current user.
If the user has no access to Structure plugin, returns empty list.
If StructureAuth.isSecurityOverridden()
is true, ignores all of the checks above and returns
all structures that the specified user owns.
The resulting list is sorted by name, using the current user's locale.
user
- owner of the structures to look forStructure.getOwner()
@NotNull List<Structure> getStructuresByName(@Nullable String name, @Nullable PermissionLevel requiredLevel)
Convenience method to search for unarchived structures with the specified name. Using this method is more efficient than retrieving all structures and filtering.
Structures are not required to have unique names, therefore this method returns a list.
Returns only structures for which the current user has access at
the specified permission level.
If the user has no access to Structure plugin, returns empty list.
If StructureAuth.isSecurityOverridden()
is true, ignores all of the checks above.
The resulting list is sorted by name, using the current user's locale.
name
- the name of the structure sought, case-insensitive and trim-insensitive
(leading and trailing whitespace don't matter). If null
, an empty list is returned.requiredLevel
- when checking for user's permission, require that the user has at least the specified permission
for every structure in the returned list.
Passing null or PermissionLevel.NONE
effectively disables the structure permissions check, but we still
check that the user has access to Structure plugin (unless StructureAuth.isSecurityOverridden()
is true).@NotNull List<Structure> getStructuresByName(@Nullable String name, @Nullable PermissionLevel requiredLevel, boolean searchArchivedStructures)
Convenience method that searches for structures with the specified name. It is more efficient than retrieving all structures and filtering.
Structures are not required to have unique names, therefore this method returns a list.
Returns only structures for which the current user has access at
the specified permission level.
If the user has no access to Structure plugin, returns empty list.
If StructureAuth.isSecurityOverridden()
is true, ignores all of the checks above.
The resulting list is sorted by name, using the current user's locale.
name
- the name of the structure sought, case-insensitive and trim-insensitive
(leading and trailing whitespace don't matter). If null
, an empty list is returned.requiredLevel
- when checking for user's permission, require that the user has at least the specified permission
for every structure in the returned list.
Passing null or PermissionLevel.NONE
effectively disables the structure permissions check, but we still
check that the user has access to Structure plugin (unless StructureAuth.isSecurityOverridden()
is true).searchArchivedStructures
- if true, result will also contain archived structuresboolean hasNonArchivedStructuresForUser()
Convenience method that checks whether the current user can see at least one
unarchived structure. This works functionally the same as
!getAllStructures(PermissionLevel.VIEW).isEmpty()
,
but much faster.
If the user has no access to Structure plugin, returns false.
(Unless StructureAuth.isSecurityOverridden()
is on, in which case user's access to Structure is not
checked.)
StructureAuth.isSecurityOverridden()
is true)
and if there exists at least one unarchived structure, to which the current user has PermissionLevel.VIEW
access.@Nullable Long getSingleViewableStructureId()
Convenience method that returns the ID of a single structure that the
current user can see.
This works much faster than getAllStructures(PermissionLevel.VIEW)
.
If the user does not have PermissionLevel.VIEW
access to any structure,
or if the user has the access to more than one structure, this method returns null
.
Also, if the user has no access to the Structure plugin, returns null.
Note that the resulting structure may be archived.
Note that this method ignores StructureAuth.isSecurityOverridden()
, unlike most other methods.
null
otherwiseboolean isIssueInStructureNoAccessCheck(@Nullable Long issueId, @Nullable Long structureId)
Checks if a specific issue (not row!) belongs to a specific structure.
Only issues that have been manually added to the structure are checked. Issues that have been added or removed by generators are not checked.
This method does not perform any permission checks.
issueId
- the ID of the issue. Nullable for convenience - if null, returns falsestructureId
- the ID of the structure. Nullable for convenience - if null, returns false@NotNull List<Structure> getViewableStructuresWithIssue(@Nullable Long issueId)
Retrieves all structures that contain the specified issue. This is functionally the same as checking every forest manually, but much faster.
Only issues that have been manually added to the structure are checked. Issues that have been added or removed by generators are not checked.
Note that forest changes may happen asynchronously, so consistency for the returned list is not guaranteed. All we can say is that each structure in the returned list either contains the specified issue or has contained it recently.
This method returns only the structures that the current user can see.
If the user has no access to Structure plugin, returns empty list.
If StructureAuth.isSecurityOverridden()
is true, these checks are not performed.
The resulting list is sorted by name, using the current user's locale.
issueId
- the ID of the issue. Nullable for convenience - if null
, returns empty list@NotNull PermissionLevel getStructurePermission(@Nullable Long structureId)
Calculates access level to a structure for the current user.
If the user is not allowed to use Structure plugin, the result will always be PermissionLevel.NONE
.
Note that this method ignores StructureAuth.isSecurityOverridden()
, unlike most other methods.
structureId
- the ID of the structure checked. Nullable for convenience - if null
, returns NONE
@NotNull PermissionLevel getStructurePermission(@Nullable Long structureId, @Nullable ApplicationUser user)
Calculates access level to a structure for the specified user.
If the user is not allowed to use Structure plugin, the result will always be PermissionLevel.NONE
.
Note that StructureAuth.isSecurityOverridden()
is not applicable here.
structureId
- the ID of the structure checked. Nullable for convenience - if null
, returns NONE
user
- the user to check permissions for, null
for anonymousboolean isAccessible(@Nullable Long structureId, @Nullable PermissionLevel requiredLevel)
Checks that the specified structure exists and the current user has access to it with the required permission level.
If structureId is null, or structure with that ID does not exist, false is returned.
If the user has no access to Structure plugin, returns false
(unless StructureAuth.isSecurityOverridden()
is true).
structureId
- the ID of the structure. Nullable for convenience - if null
, returns false
requiredLevel
- when checking for user's permission, require that the user
has at least the specified permission level for the structure.
Passing null or PermissionLevel.NONE
effectively disables the structure permissions check, but we still
check that the user has access to Structure plugin (unless StructureAuth.isSecurityOverridden()
is true).boolean isGeneratorConfigurationAllowed(@Nullable Long structureId, @Nullable ApplicationUser user)
Checks that the specified user has the
CONFIGURE_GENERATORS
app permission and has at least AUTOMATE
access level to the specified structure.
Note that StructureAuth.isSecurityOverridden()
is not applicable here.
structureId
- the ID of the structure checked. Nullable for convenience - if null
, returns false
user
- the user to check permissions for, null
for anonymousboolean isEffectorConfigurationAllowed(@Nullable Long structureId, @Nullable ApplicationUser user)
Checks that the specified user has the
CONFIGURE_EFFECTORS
app permission and has at least AUTOMATE
access level to the specified structure.
Note that StructureAuth.isSecurityOverridden()
is not applicable here.
structureId
- the ID of the structure checked. Nullable for convenience - if null
, returns false
user
- the user to check permissions for, null
for anonymousboolean isEffectorExecutionAllowed(@Nullable Long structureId, @Nullable ApplicationUser user)
Checks that the specified user has the
EXECUTE_EFFECTORS
app permission and has at least VIEW
access level to the specified structure.
Note that StructureAuth.isSecurityOverridden()
is not applicable here.
structureId
- the ID of the structure checked. Nullable for convenience - if null
, returns false
user
- the user to check permissions for, null
for anonymous@NotNull Structure createStructure()
Creates an empty new structure. The structure returned is not yet persisted - you need to call the required
setter methods and then call Structure.saveChanges()
to write the new structure to the database
and be able to fill it with items.
The structure will have the current user as its owner.
This method checks that the current user can use Structure plugin and can create structures, unless
StructureAuth.isSecurityOverridden()
is true.
Note that in order to write the contents of the structure you need to obtain an instance of
ForestSource
from ForestService
:
StructureManager sm = ... ForestService fs = ... Structure s = sm.createStructure().setName("new structure").saveChanges(); ForestSpec spec = ForestSpec.structure(s.getId()); ForestSource ufs = fs.getForestSource(spec); ufs.apply(new Add(CoreIdentities.issue(issueId), 0, 0, 0));
@NotNull Structure copyStructure(@Nullable Long structureId, @Nullable ApplicationUser newOwner, boolean copyPermissions) throws StructureException
Copies the structure and the forest it contains into a new structure.
This method checks that the current user has all required permissions:
to use Structure plugin, to create structures, and to view
the copied structure;
also, requires PermissionLevel.ADMIN
access to copy permissions.
All these checks are not performed if StructureAuth.isSecurityOverridden()
is true.
structureId
- the ID of the structure. Nullable for convenience - if null
, throws exceptionnewOwner
- the user who will be the owner of the new structure, if null - keep the old ownercopyPermissions
- if true, the permission list will be copied - this requires ADMIN permission level to the
original structure, if the user does not have it, StructureException is thrownStructure.getId()
to learn its IDStructureException
- if the copied structure doesn't exist, the user has not enough permissions, or any other problem happens@NotNull Structure copyStructureWithoutForest(@Nullable Long structureId, @Nullable ApplicationUser newOwner, boolean copyPermissions) throws StructureException
Copies the structure into a new structure - only the properties (such as name, description, permissions) are copied, not the forest.
This method checks that the current user has all required permissions:
to use Structure plugin, to create structures, and to view
the copied structure;
also, requires PermissionLevel.ADMIN
access to copy permissions.
All these checks are not performed if StructureAuth.isSecurityOverridden()
is true.
structureId
- the ID of the structure. Nullable for convenience - if null
, throws exceptionnewOwner
- the user who will be the owner of the new structure, if null - keep the old ownercopyPermissions
- if true, the permission list will be copied - this requires ADMIN permission level to the
original structure, if the user does not have it, StructureException is thrownStructure.getId()
to learn its IDStructureException
- if the copied structure doesn't exist, the user has not enough permissions, or any other problem happensvoid deleteStructure(@Nullable Long id) throws StructureException
Deletes the specified structure and its content.
JIRA items such as issues or projects are not themselves deleted. Structure-owned items such as folders or generators are deleted.
This method checks that the current user can use Structure plugin and has
PermissionLevel.ADMIN
access to the specified structure.
These checks are waived if StructureAuth.isSecurityOverridden()
is true.
This method will dispatch the StructureDeletedEvent
after
structure deleting. An event listener can be registered using JIRA notification system.
id
- the ID of the structure. Nullable for convenience - if null
, throws exceptionStructureException
- if the structure doesn't exist, is not accessible at ADMIN permission level, or there's problem deleting structurevoid addListener(@NotNull StructureListener listener)
Adds a structure listener. Whenever structure's static content is changed, the listeners are called synchronously after the changes are persisted.
See StructureListener
for details about listener contract.
listener
- the listenerStructureListener
void removeListener(@NotNull StructureListener listener)
Removes the listener previously added via addListener(StructureListener)
.
listener
- listener to be removedCopyright © 2024 Tempo Software. All Rights Reserved.