Because a Security Profile Item in "core" is not a Schema
And you're going about it wrong.
To reach the "schema" for a user
If you want to read all available fields defined for your user, you will have to refer to the definition you have defined for your user, which would be the Sitecore Security Profile. And essentially it would involve reading it and looping through the defined fields. But the Security Profile item in "core" really shouldn't be your guide here; instead YOU define what properties should be shown for any user and go from there.
To read properties for a user
For the user itself, you will only ever get profile fields and values that have been set on that specific user. Changing the Security Profile definition in "core" does nothing to update your existing users - it is simply there to give Sitecore a basic UI for user editing. For convenience.
As a side note; the fact that it is stored in "core" should give this away. "Core" is the Sitecore database from which the Sitecore UI runs - nothing else.
Further
Underneath the Sitecore Profile Provider lies a completely standard ASP.NET Profile Provider. In a very simplified form, GetPropertyValues
for a user is done by executing the dbo.aspnet_Profile_GetProperties
Stored Procedure, and then splitting the key/value pairs on :
.
connectionHolder = SqlConnectionHelper.GetConnection(this._sqlConnectionString, true);
this.CheckSchemaVersion(connectionHolder.Connection);
SqlCommand sqlCommand = new SqlCommand("dbo.aspnet_Profile_GetProperties", connectionHolder.Connection);
sqlCommand.CommandTimeout = this.CommandTimeout;
sqlCommand.CommandType = CommandType.StoredProcedure;
sqlCommand.Parameters.Add(this.CreateInputParam("@ApplicationName", SqlDbType.NVarChar, (object) this.ApplicationName));
sqlCommand.Parameters.Add(this.CreateInputParam("@UserName", SqlDbType.NVarChar, (object) userName));
sqlCommand.Parameters.Add(this.CreateInputParam("@CurrentTimeUtc", SqlDbType.DateTime, (object) DateTime.UtcNow));
sqlDataReader = sqlCommand.ExecuteReader(CommandBehavior.SingleRow);
if (sqlDataReader.Read())
{
names = sqlDataReader.GetString(0).Split(':');
values = sqlDataReader.GetString(1);
int bytes = (int) sqlDataReader.GetBytes(2, 0L, (byte[]) null, 0, 0);
numArray = new byte[bytes];
sqlDataReader.GetBytes(2, 0L, numArray, 0, bytes);
Notice how this code makes no references to any User Profile "definition" of sorts. At this level; profile attributes are just treated as key/value pairs.