0 votes
8 views
by

I've been testing out a component where one can programmatically create a field in the user object. It's being used to allow a user to check a few boxes that'll filter components in pages (using the lightning page component filtering) that is unique to that user.

With this test I've met an annoying problem. If I manually create the field, it's all good because we get to decide the field level access. But when I create it programmatically it comes with zero access to any users even my own (sys admin).

The way I'* creating the field is:

global with sharing class FieldGen {
        //@future(callout = true)
        global static void makeCreateUserFieldCallout(String intendedName){
            String objectapiname = 'User';
        
        /* assertFieldName just makes name acceptable for the API name of the field. */
        String fieldapiname = TogglerCtrlApex.assertFieldName(intendedName, true);
        String fieldlabel = TogglerCtrlApex.assertFieldName(intendedName, false);
        String fielddescription = 'Field created for topic visibility toggler component!';
        
        try{
            HttpRequest requestinside = new HttpRequest();
            requestinside.setHeader('Authorization', 'Bearer ' + UserInfo.getSessionID());
            requestinside.setHeader('Content-Type', 'application/json');
            requestinside.setEndpoint(URL.getSalesforceBaseUrl().toExternalForm()+'/services/data/v26.0/tooling/sobjects/CustomField/');
            requestinside.setMethod('POST');
            String fieldDef = '{"Metadata" : ';
            String metadef = '"type" : "Checkbox","description" : "'+fielddescription+'","defaultValue":"true", "inlineHelpText" : "","precision" : null,"label" : "'+fieldlabel+'","required" : false';
            fieldDef += '{'+metadef+'},';
            fieldDef += '"FullName" : "'+objectapiname+'.'+fieldapiname+'"}';
            system.debug(fieldDef);
            requestinside.setBody(fieldDef);
            Http http = new Http();
            HTTPResponse res = http.send(requestinside);
            System.debug(res.getBody());
        }
        catch(Exception e){
            System.debug(e.getMessage());
        }
    }
}

Basically using the API to create a field in the User Object. Unfortunatelly it doesn't give access though =/

I've been experimenting with the MetadataService class to try to add field permissions to a permission set when the field is created. This isn't working though and the documentation for this class is very slim. This is what I have so far:

public with sharing class MetadataServiceExamples
{
    @future(callout = true)
    public static void testPerm()
    {
        /* Find the Quick Toggler Permission Set! */
        MetadataService.MetadataPort service = createService();
        String[] permissionSetNames = new String[] {'Quick_Visibility_Toggler_Permissions'};
        List<MetadataService.PermissionSet> perm = 
            (List<MetadataService.PermissionSet>) service.readMetadata('PermissionSet', permissionSetNames).getRecords();
        MetadataService.PermissionSet quickPerm = perm.get(0);
        System.debug('Test: ' + quickPerm.fieldPermissions);
        MetadataService.PermissionSetFieldPermissions fieldSec = new MetadataService.PermissionSetFieldPermissions();
        fieldSec.field='User.TestFieldA__c';
        fieldSec.editable=true;
        fieldSec.readable=true;
        quickPerm.fieldPermissions.add(fieldSec);// = new MetadataService.PermissionSetFieldPermissions[] {fieldSec} ;
        System.debug('Test: ' + quickPerm.fieldPermissions);
        List<MetadataService.SaveResult> results =
            service.updateMetadata(
                new MetadataService.Metadata[] { quickPerm });
        System.debug('Results: ' + results);
        //handleSaveResults(results[0]);
    }
}

It seems I can't access and change the permission set though. WIth that being said, does anyone know of a way I could either add CRUD permissions for the new field to a permission set or a profile programmatically right after the field is created?

1 Answer

0 votes
by
 
Best answer

You can Provide Field Permission to permission set by creating FieldPermissions record like this

FieldPermissions fp= new FieldPermissions();
fp.Field='Case.AccountId';//the name of new field
fp.ParentId='0PS0o000001WP6AGAW';// id of permission set 
fp.PermissionsEdit=true;//
fp.PermissionsRead=true;
fp.SobjectType='Case';
Insert fp; 

though this only works for permission set here is the link for object https://developer.salesforce.com/docs/atlas.en-us.object_reference.meta/object_reference/sforce_api_objects_fieldpermissions.htm

Welcome to Memory Exceeded, where you can ask questions and receive answers from other members of the community.
...