11

this one is weird I hope somebody can help me.

I created a custom action for a callout on a document library. I added the javascript code in a code snippet webpart on top of the document library default view.

When I click on the left navigation menu to go to the library, the code throws this exception when I click on the 3 dots.

Uncaught TypeError: Cannot read property 'get_current' of undefined 

If I press Ctrl + F5, the code works fine.

<script type="text/javascript">
    SP.SOD.executeFunc("callout.js", "Callout", function () {
        IsCurrentUserMemberOfGroup("Approvers", function(isSuccess){
            if(isSuccess){
                var itemCtx = {};
                itemCtx.Templates = {};
                itemCtx.BaseViewID = 'Callout';
                // Define the list template type
                itemCtx.ListTemplateType = 101;

                itemCtx.Templates.Footer = function (itemCtx) {             
                  return CalloutRenderFooterTemplate(itemCtx, AddCustomCompleteAction, true);
                };  

                SPClientTemplates.TemplateManager.RegisterTemplateOverrides(itemCtx);
            }               
        });
    });


    function AddCustomCompleteAction (renderCtx, calloutActionMenu) {  
        var Status = renderCtx.CurrentItem.Status;

        if(renderCtx.CurrentItem.ContentType=='Bill Cycle'  && Status=='') {
                calloutActionMenu.addAction (new CalloutAction ({
                text: 'COMPLETE',
                tooltip: 'This action will set status to Complete, this action cant be rolled back. Only click once the action can take a few seconds to complete.',
                onClickCallback: function() {UpdateBillCycleStatusToCompleted(renderCtx.CurrentItem.ID);}
            }));            
        }

        // Show the default document library actions
        CalloutOnPostRenderTemplate(renderCtx, calloutActionMenu);

         // Show the follow action
          calloutActionMenu.addAction(new CalloutAction({
            text: Strings.STS.L_CalloutFollowAction,
            tooltip: Strings.STS.L_CalloutFollowAction_Tooltip,
            onClickCallback: function (calloutActionClickEvent, calloutAction) {
              var callout = GetCalloutFromRenderCtx(renderCtx);
              if (!(typeof(callout) === 'undefined' || callout === null))
                callout.close();
              SP.SOD.executeFunc('followingcommon.js', 'FollowSelectedDocument', function() { FollowSelectedDocument(renderCtx); });
            }
          }));
    }   

    function UpdateBillCycleStatusToCompleted(itemId) {
        var clientContext = new SP.ClientContext.get_current();
        var oList = clientContext.get_web().get_lists().getByTitle('Cycles');
        this.oListItem = oList.getItemById(itemId);
        oListItem.set_item('Status', 'Completed');
        oListItem.update();
        clientContext.executeQueryAsync(Function.createDelegate(this, this.StatusCompletedSucceeded), Function.createDelegate(this, this.StatusCompletedFailed));
    }

    function StatusCompletedSucceeded() {
        alert(' set to completed succeeded');
        window.location.reload(true);
    }

    function StatusCompletedFailed(sender, args) {
        alert(' update failed. ' + args.get_message() + '\n' + args.get_stackTrace());
    }

    function IsCurrentUserMemberOfGroup(groupName, callback) {
        var currentContext = new SP.ClientContext.get_current();
        var currentWeb = currentContext.get_web();

        var currentUser = currentContext.get_web().get_currentUser();
        currentContext.load(currentUser);

        var allGroups = currentWeb.get_siteGroups();
        currentContext.load(allGroups);

        var group = allGroups.getByName(groupName);
        currentContext.load(group);

        var groupUsers = group.get_users();
        currentContext.load(groupUsers);

        currentContext.executeQueryAsync(OnSuccess,OnFailure);

        function OnSuccess(sender, args) {
            var userInGroup = false;
            var groupUserEnumerator = groupUsers.getEnumerator();
            while (groupUserEnumerator.moveNext()) {
                var groupUser = groupUserEnumerator.get_current();
                if (groupUser.get_id() == currentUser.get_id()) {
                    userInGroup = true;
                    break;
                }
            }  
            callback(userInGroup);
        }

        function OnFailure(sender, args) {
            callback(false);
        }        
    }
</script>

4 Answers 4

17

Since you are using SP.ClientContext in CSR, make sure the SharePoint script file 'sp.js' is loaded before your rendering code runs:

SP.SOD.executeFunc('sp.js', 'SP.ClientContext', function(){
 //Your code goes here...
});
9

fixed with this

$(document).ready(function () { ExecuteOrDelayUntilScriptLoaded(CustomAction, "sp.js"); });

    function CustomAction()

    {
           //Your Code
    }
3

This works for me when I am using WorkflowServices. It should work in your case as well:

ExecuteOrDelayUntilScriptLoaded(function () {
    ExecuteOrDelayUntilScriptLoaded(function () {
        SP.SOD.registerSod('SP.ClientContext', SP.Utilities.Utility.getLayoutsPageUrl('sp.js'));
        SP.SOD.registerSod('SP.WorkflowServices.WorkflowServicesManager', SP.Utilities.Utility.getLayoutsPageUrl('SP.WorkflowServices.js'));
        SP.SOD.loadMultiple(['SP.ClientContext', 'SP.WorkflowServices.WorkflowServicesManager'], function () {
            var context = SP.ClientContext.get_current();
            var web = context.get_web();
            var servicesManager = SP.WorkflowServices.WorkflowServicesManager.newObject(context, web);
            var instanceService = servicesManager.getWorkflowInstanceService();
        });
    }, "sp.js");
}, "sp.runtime.js");
1
  • Please don't add the same answer as this one Try to be more specific. Thank you
    – Benny Skogberg
    Aug 26, 2016 at 14:50
0

Elaborating more on Vadim solution:

function retrieveWebSite() {
       SP.SOD.executeFunc('sp.js', 'SP.ClientContext', function(){
            var clientContext = new SP.ClientContext.get_current();
            this.oWebsite = clientContext.get_web();
            clientContext.load(this.oWebsite);

        clientContext.executeQueryAsync(
           Function.createDelegate(this, this.onQuerySucceeded), 
           Function.createDelegate(this, this.onQueryFailed)
        );
   });
}

 function onQuerySucceeded(sender, args) {
     alert('Title: ' + this.oWebsite.get_title() + 
    ' Description: ' + this.oWebsite.get_description());
 } 

function onQueryFailed(sender, args) {
     alert('Request failed. ' + args.get_message() + 
    '\n' + args.get_stackTrace());
 }

In HTML

 <input type="button" onclick="retrieveWebSite()" value="Click"/>

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.