001 /*
002 * Copyright 2011-2012 UnboundID Corp.
003 *
004 * This program is free software; you can redistribute it and/or modify
005 * it under the terms of the GNU General Public License (GPLv2 only)
006 * or the terms of the GNU Lesser General Public License (LGPLv2.1 only)
007 * as published by the Free Software Foundation.
008 *
009 * This program is distributed in the hope that it will be useful,
010 * but WITHOUT ANY WARRANTY; without even the implied warranty of
011 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
012 * GNU General Public License for more details.
013 *
014 * You should have received a copy of the GNU General Public License
015 * along with this program; if not, see <http://www.gnu.org/licenses>.
016 */
017
018 package com.unboundid.scim.sdk;
019
020 import java.util.regex.Matcher;
021 import java.util.regex.Pattern;
022
023
024
025 /**
026 * This class represents a path to an attribute or sub-attribute. The path is
027 * a string comprising an schema URI (the SCIM core schema is assumed
028 * if absent), an attribute name, and an optional sub-attribute name.
029 */
030 public class AttributePath
031 {
032 /**
033 * A regular expression to match the components of an attribute path.
034 * Given the path "urn:scim:schemas:core:user:1.0:name.familyName" then
035 * group 2 will match "urn:scim:schemas:core:user:1.0", group 3 matches
036 * "name" and group 5 matches "familyName".
037 */
038 private static final Pattern pattern =
039 Pattern.compile("^((.+):)?([^.]+)(\\.(.+))?$");
040
041 /**
042 * The URI of the attribute schema.
043 */
044 private final String attributeSchema;
045
046 /**
047 * The name of the attribute.
048 */
049 private final String attributeName;
050
051 /**
052 * The name of the sub-attribute, or {@code null} if absent.
053 */
054 private final String subAttributeName;
055
056
057
058 /**
059 * Create a new attribute path.
060 *
061 * @param attributeSchema The URI of the attribute schema.
062 * @param attributeName The name of the attribute.
063 * @param subAttributeName The name of the sub-attribute, or {@code null} if
064 * absent.
065 */
066 public AttributePath(final String attributeSchema,
067 final String attributeName,
068 final String subAttributeName)
069 {
070 this.attributeSchema = attributeSchema;
071 this.attributeName = attributeName;
072 this.subAttributeName = subAttributeName;
073 }
074
075
076
077 /**
078 * Parse an attribute path.
079 *
080 * @param path The attribute path.
081 *
082 * @return The parsed attribute path.
083 */
084 public static AttributePath parse(final String path)
085 {
086 final Matcher matcher = pattern.matcher(path);
087
088 if (!matcher.matches() || matcher.groupCount() != 5)
089 {
090 throw new IllegalArgumentException(
091 String.format(
092 "'%s' does not match '[schema:]attr[.sub-attr]' format", path));
093 }
094
095 final String attributeSchema = matcher.group(2);
096 final String attributeName = matcher.group(3);
097 final String subAttributeName = matcher.group(5);
098
099 if (attributeSchema != null)
100 {
101 return new AttributePath(attributeSchema, attributeName,
102 subAttributeName);
103 }
104 else
105 {
106 return new AttributePath(SCIMConstants.SCHEMA_URI_CORE, attributeName,
107 subAttributeName);
108 }
109 }
110
111
112
113 /**
114 * {@inheritDoc}
115 */
116 @Override
117 public String toString()
118 {
119 final StringBuilder builder = new StringBuilder();
120 toString(builder);
121 return builder.toString();
122 }
123
124
125
126 /**
127 * Append the string representation of the attribute path to the provided
128 * buffer.
129 *
130 * @param builder The buffer to which the string representation of the
131 * attribute path is to be appended.
132 */
133 public void toString(final StringBuilder builder)
134 {
135 if (!attributeSchema.equalsIgnoreCase(SCIMConstants.SCHEMA_URI_CORE))
136 {
137 builder.append(attributeSchema);
138 builder.append(':');
139 }
140
141 builder.append(attributeName);
142 if (subAttributeName != null)
143 {
144 builder.append('.');
145 builder.append(subAttributeName);
146 }
147 }
148
149
150
151 /**
152 * Retrieve the URI of the attribute schema.
153 * @return The URI of the attribute schema.
154 */
155 public String getAttributeSchema()
156 {
157 return attributeSchema;
158 }
159
160
161
162 /**
163 * Retrieve the name of the attribute.
164 * @return The name of the attribute.
165 */
166 public String getAttributeName()
167 {
168 return attributeName;
169 }
170
171
172
173 /**
174 * Retrieve the name of the sub-attribute, or {@code null} if absent.
175 * @return The name of the sub-attribute, or {@code null} if absent.
176 */
177 public String getSubAttributeName()
178 {
179 return subAttributeName;
180 }
181 }