001package gov.nist.secauto.oscal.lib.model;
002
003import gov.nist.secauto.metaschema.core.datatype.adapter.UuidAdapter;
004import gov.nist.secauto.metaschema.core.model.IBoundObject;
005import gov.nist.secauto.metaschema.core.model.IMetaschemaData;
006import gov.nist.secauto.metaschema.core.model.JsonGroupAsBehavior;
007import gov.nist.secauto.metaschema.core.model.constraint.IConstraint;
008import gov.nist.secauto.metaschema.core.util.ObjectUtils;
009import gov.nist.secauto.metaschema.databind.model.annotations.AssemblyConstraints;
010import gov.nist.secauto.metaschema.databind.model.annotations.BoundAssembly;
011import gov.nist.secauto.metaschema.databind.model.annotations.BoundFlag;
012import gov.nist.secauto.metaschema.databind.model.annotations.GroupAs;
013import gov.nist.secauto.metaschema.databind.model.annotations.IsUnique;
014import gov.nist.secauto.metaschema.databind.model.annotations.KeyField;
015import gov.nist.secauto.metaschema.databind.model.annotations.MetaschemaAssembly;
016import java.lang.Override;
017import java.lang.String;
018import java.util.LinkedList;
019import java.util.List;
020import java.util.UUID;
021import org.apache.commons.lang3.builder.ReflectionToStringBuilder;
022import org.apache.commons.lang3.builder.ToStringStyle;
023
024/**
025 * Each OSCAL profile is defined by a <code>profile</code> element.
026 */
027@MetaschemaAssembly(
028    formalName = "Profile",
029    description = "Each OSCAL profile is defined by a `profile` element.",
030    name = "profile",
031    moduleClass = OscalProfileModule.class,
032    rootName = "profile",
033    remarks = "An OSCAL document that describes a tailoring of controls from one or more catalogs, with possible modification of multiple controls. It provides mechanisms by which controls may be selected (`import`), merged or (re)structured (`merge`), and amended (`modify`). OSCAL profiles may select subsets of controls, set parameter values for them in application, and even adjust the representation of controls as given in and by a catalog. They may also serve as sources for further modification in and by other profiles, that import them.",
034    modelConstraints = @AssemblyConstraints(unique = {@IsUnique(id = "oscal-unique-document-id", formalName = "Unique Document Identifier", description = "Ensure all document identifiers have a unique combination of @scheme and value.", level = IConstraint.Level.ERROR, target = "document-id", keyFields = {@KeyField(target = "@scheme"), @KeyField}), @IsUnique(id = "oscal-unique-property-in-context-location", formalName = "Unique Properties", description = "Ensure all properties are unique for a given location using a unique combination of @ns, @name, @class. @group. and @value.", level = IConstraint.Level.ERROR, target = ".//prop", keyFields = {@KeyField(target = "path(..)"), @KeyField(target = "@name"), @KeyField(target = "@ns"), @KeyField(target = "@class"), @KeyField(target = "@group"), @KeyField(target = "@value")}), @IsUnique(id = "oscal-unique-link-in-context-location", formalName = "Unique Links", description = "Ensure all links are unique for a given location using a unique combination of @href, @rel, and @media-type.", level = IConstraint.Level.ERROR, target = ".//link", keyFields = {@KeyField(target = "path(..)"), @KeyField(target = "@href"), @KeyField(target = "@rel"), @KeyField(target = "@media-type")}), @IsUnique(id = "oscal-unique-responsibility-in-context-location", formalName = "Unique Responsibilities", description = "Ensure all responsible-roles and responsible-parties are unique for a given location using a unique combination of @role-id and the combination of @party-uuid values.", level = IConstraint.Level.ERROR, target = ".//(responsible-party|responsible-role)", keyFields = {@KeyField(target = "path(..)"), @KeyField(target = "@role-id"), @KeyField(target = "@party-uuid")}, remarks = "Since `responsible-party` and `responsible-role` associate multiple `party-uuid` entries with a single `role-id`, each role-id must be referenced only once.")})
035)
036public class Profile extends AbstractOscalInstance implements IBoundObject {
037  private final IMetaschemaData __metaschemaData;
038
039  /**
040   * "Provides a globally unique means to identify a given profile instance."
041   */
042  @BoundFlag(
043      formalName = "Profile Universally Unique Identifier",
044      description = "Provides a globally unique means to identify a given profile instance.",
045      name = "uuid",
046      required = true,
047      typeAdapter = UuidAdapter.class
048  )
049  private UUID _uuid;
050
051  @BoundAssembly(
052      formalName = "Document Metadata",
053      description = "Provides information about the containing document, and defines concepts that are shared across the document.",
054      useName = "metadata",
055      minOccurs = 1
056  )
057  private Metadata _metadata;
058
059  @BoundAssembly(
060      formalName = "Import Resource",
061      description = "Designates a referenced source catalog or profile that provides a source of control information for use in creating a new overlay or baseline.",
062      useName = "import",
063      minOccurs = 1,
064      maxOccurs = -1,
065      groupAs = @GroupAs(name = "imports", inJson = JsonGroupAsBehavior.LIST)
066  )
067  private List<ProfileImport> _imports;
068
069  @BoundAssembly(
070      formalName = "Merge Controls",
071      description = "Provides structuring directives that instruct how controls are organized after profile resolution.",
072      useName = "merge"
073  )
074  private Merge _merge;
075
076  @BoundAssembly(
077      formalName = "Modify Controls",
078      description = "Set parameters or amend controls in resolution.",
079      useName = "modify"
080  )
081  private Modify _modify;
082
083  @BoundAssembly(
084      formalName = "Back matter",
085      description = "A collection of resources that may be referenced from within the OSCAL document instance.",
086      useName = "back-matter"
087  )
088  private BackMatter _backMatter;
089
090  public Profile() {
091    this(null);
092  }
093
094  public Profile(IMetaschemaData data) {
095    this.__metaschemaData = data;
096  }
097
098  @Override
099  public IMetaschemaData getMetaschemaData() {
100    return __metaschemaData;
101  }
102
103  public UUID getUuid() {
104    return _uuid;
105  }
106
107  public void setUuid(UUID value) {
108    _uuid = value;
109  }
110
111  public Metadata getMetadata() {
112    return _metadata;
113  }
114
115  public void setMetadata(Metadata value) {
116    _metadata = value;
117  }
118
119  public List<ProfileImport> getImports() {
120    return _imports;
121  }
122
123  public void setImports(List<ProfileImport> value) {
124    _imports = value;
125  }
126
127  /**
128   * Add a new {@link ProfileImport} item to the underlying collection.
129   * @param item the item to add
130   * @return {@code true}
131   */
132  public boolean addImport(ProfileImport item) {
133    ProfileImport value = ObjectUtils.requireNonNull(item,"item cannot be null");
134    if (_imports == null) {
135      _imports = new LinkedList<>();
136    }
137    return _imports.add(value);
138  }
139
140  /**
141   * Remove the first matching {@link ProfileImport} item from the underlying collection.
142   * @param item the item to remove
143   * @return {@code true} if the item was removed or {@code false} otherwise
144   */
145  public boolean removeImport(ProfileImport item) {
146    ProfileImport value = ObjectUtils.requireNonNull(item,"item cannot be null");
147    return _imports != null && _imports.remove(value);
148  }
149
150  public Merge getMerge() {
151    return _merge;
152  }
153
154  public void setMerge(Merge value) {
155    _merge = value;
156  }
157
158  public Modify getModify() {
159    return _modify;
160  }
161
162  public void setModify(Modify value) {
163    _modify = value;
164  }
165
166  public BackMatter getBackMatter() {
167    return _backMatter;
168  }
169
170  public void setBackMatter(BackMatter value) {
171    _backMatter = value;
172  }
173
174  @Override
175  public String toString() {
176    return new ReflectionToStringBuilder(this, ToStringStyle.MULTI_LINE_STYLE).toString();
177  }
178}