function readOnly(count){ }
Starting November 20, the site will be set to read-only. On December 4, 2023,
forum discussions will move to the Trailblazer Community.
+ Start a Discussion
Jon Mountjoy_Jon Mountjoy_ 

Metadata API - some success, though UNKNOWN_EXCEPTION when changing Tab visibility

I can successfully create an object and tab using the metadata API.  However, the tab isn't visible by default (uh), so I have to change the user profile information to correct.

However, when I try and do this using the update() method I get
An unexpected error occurred.

Can you tell me how to do the tab visibility update?  Am I doing something wrong?

Profile p = new Profile();
ProfileTabVisibility ptv = new ProfileTabVisibility("MyCustomObject__c",TabVisibility.DefaultOn );
ProfileTabVisibility[] tabVisibilities = new ProfileTabVisibility[] {ptv };
UpdateMetadata pum = new UpdateMetadata("Admin", p);
AsyncResult[] ars3 = (AsyncResult[]) metadatabinding.update(new UpdateMetadata[] { pum });

 The tab does exist, it does have that name, and the "Admin" profile does exist.


Based on a quick look at your code, you are not setting the fullName of the Profile p. Try p.setFullName("Admin") before making the update call. That should resolve this issue. If not let me know and I shall look deeper into it.

Jon Mountjoy_Jon Mountjoy_
Excellent advice Akhilesh - that solved that problem!

There is still a subtle security problem going on. I can now create the tab and grant visibility to the profile, as the code above now does with your addition. However, I can't actually "see" the tab when I then go and log in and add the tab.

In other words, the tab is now available to me to choose to add to my set of visible tabs, but it doesn't appear - even though I've added it to an app.

I can solve it by going to the profile page for system administrator, hitting "Edit", then hitting "Save"! ie. I don't change anything (that I know of). It's really odd.

Obviously I need to do more than just setTabVisiblity() on the profile - I'll let you know when I figure out just what that is....

Jon Mountjoy_Jon Mountjoy_
Investigating even further, I grabbed all the metadata from the org both before and after the "edit/save" of the profile - which suddenly makes everything work.

Doing a diff -r dir1 dir2 on each directory of metadata, I see no changes.

So somehow doing an edit/save on a profile changes something, which isn't reflected in the metadata, and which makes everything start working.....hmmmmmm

Ramesh GudepuRamesh Gudepu
Dear akhilesh_sfdc,

i have same issue but i need to disable custom application from System Admin profile using Metadata API.i wrote java code for disabling custom app from Admin profile and it is giving error.please help me.

java code: 

import com.sforce.soap.enterprise.EnterpriseConnection;
import com.sforce.soap.enterprise.LoginResult;
import com.sforce.soap.metadata.AsyncResult;
import com.sforce.soap.metadata.Metadata;
import com.sforce.soap.metadata.MetadataConnection;
import com.sforce.soap.metadata.Profile;
import com.sforce.soap.metadata.ProfileApplicationVisibility;

public class CustomApp {
MetadataConnection metadataconnection;
ConnectorConfig metaConfig;

private void disableCustomApp(String endpoint, String metaUserName, String metaPassword) throws Exception {
  getMetaConnection( endpoint, metaUserName, metaPassword);
  Profile profile = new Profile();
     ProfileApplicationVisibility appVisibility =new ProfileApplicationVisibility();
        appVisibility.setApplication("Sales Automation");
        profile.setApplicationVisibilities(new ProfileApplicationVisibility[] {appVisibility});
  AsyncResult[] asyncResults = this.metadataconnection.create(new Metadata[] {profile});
  if (asyncResults == null) {
    System.out.println("The custom app was not disabled successfully");
  do {
   asyncResults = this.metadataconnection.checkStatus(new String[] {asyncResults[0].getId()});
  while (!asyncResults[0].isDone());
   System.out.println("The custom app was disabled successfully");

private void printAsyncResultStatus(AsyncResult[] asyncResults) throws Exception {
  if (asyncResults == null || asyncResults.length == 0 || asyncResults[0] == null) {
   throw new Exception("The object status cannot be retrieved");
  AsyncResult asyncResult = asyncResults[0];
  if (asyncResult.getStatusCode() != null) {
  System.out.println("Object with id:" + asyncResult.getId() + " is " + asyncResult.getState());
  System.out.println("Object with id:" + asyncResult.getId() + " is " + asyncResult.getMessage());

public void getMetaConnection(String endpoint, String metaUserName, String metaPassword){
  try {
      metaConfig = new ConnectorConfig();
   LoginResult loginResult = new EnterpriseConnection(metaConfig).login(metaUserName, metaPassword);
   metadataconnection = new MetadataConnection(metaConfig);
  } catch (ConnectionException ce) {
   throw new RuntimeException("INVALID_LOGIN", ce);

public static void main(String []args){
  CustomApp ca = new CustomApp();
  try {
   ca.disableCustomApp("", "username", "password");
  } catch (Exception e) {

Object with id:04si0000000xDFWAA2 is InProgress
Object with id:04si0000000xDFWAA2 is null
Object with id:04si0000000xDFWAA2 is Error
Object with id:04si0000000xDFWAA2 is duplicate value found: <unknown> duplicates value on record with id: <unknown>