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

Using Javascript (JQuery) in an Apex iframe



In a visualforce I used an autocomplete feature (in JQeury) for an input field and that works great.

It's based on a remote action define in my controller which is called by the javascript.


Now, I want to put my visualforce in an apex iframe but when the frame is shown, the warning message : "Javascript proxies were not generated for controller myController : may not use public remoted methods inside an iframe".

And my apex remote action is of course never called.....


Do someone has an idea to resolve that ?


Thanks in advance for your help.



Best Answer chosen by Admin (Salesforce Developers) 



I feel a little bit alone ;-)


So for those who experience this problem, simply declare as global:
- The controller of the Visualforce
- The method declared in remote action


If it can help someone, you're welcome ;-)


Enjoy !

All Answers


Can you post the code here?  (as simply as possible)




Thanks for your interest to help me.


So I tried to reduce the source code length as I can (see after) but with the elements below, you can put on a platform to test (just need jQuery as resource and JSONObject class).


Explanations for the operation :
- Visualforce page "Main" which is called manually (/apex/Main) and integrate inside an iframe
- Visualforce page "searchOpportunity" which is included in the iframe
- Apex controller "SearchOpportunityController" which is the controller of the page "searchOpportunity"


For the principle of autocomplete:
The user enters the characters (at least 3) the name of this opportunity and launcheda remoteaction in the controller which will then get a list of opportunities and thecorresponding display as a list in which the user can select the desired opportunity.

First I called the page "Main" (apex/Main), a warning (error) popup is displayed and apex remote action is never called :-(



Then I called the page "SearchOpportunity" (apex/SearchOpportunity), all works well :-) it's not enough....



But I need absolutely of course a Main page to integrate the page (as an iframe) in another GUI to integrate a sidebar, change the iframe source, etc...


Can you help me to resolve this restriction ?

Thanks in advance.


Visualforce "Main" 

<apex:page controller="MainController" showHeader="false" sidebar="false">
        <iframe height="600px" id="theIframe" name="theIframe" src="/apex/searchOpportunity" width="100%" frameborder="0"></iframe>

 Visualforce "searchOpportunity"

<apex:page controller="SearchOpportunityController" showHeader="false" sidebar="false">

<script src="{!URLFOR($Resource.jQueryFiles, 'js/jquery-1.6.2.min.js')}"></script>
<script src="{!URLFOR($Resource.jQueryFiles, 'js/jquery-ui-1.8.16.custom.min.js')}"></script>
<apex:stylesheet value="{!URLFOR($Resource.jQueryFiles, 'css/smoothness/jquery-ui-1.8.16.custom.css')}"/>
<apex:form id="formSearchOrCreateOpportunity">

    <apex:pageBlock id="pageblock" title="{!$ObjectType.Opportunity.label}">  

        <apex:pageMessages />

        <apex:outputPanel id="oppNameArea"  >
            <apex:pageBlockSection columns="1" collapsible="false"  >
                <apex:pageBlockSectionItem >
                    <!-- Opportunity field name label --> 
                    <apex:outputLabel value="{!$ObjectType.Opportunity.fields.Name.label}" />
                    <!-- Opportunity field name value and a label to indicate if new or existing opportunity -->
                    <apex:outputPanel styleClass="requiredInput" layout="block" id="pwPanel" >
                        <apex:outputPanel styleClass="requiredBlock" layout="block"/>
                        <apex:inputText id="opp_account_name" label="Opportunity name" value="{!searchedCharacters}" styleClass="inputtext autocompleteOpportunity" required="true" style="width:50%;display:block;float:left" onchange="ResetOpportunity();"/>      
                <!-- Function launched when the user enter characters to load matching opportunities -->
                <apex:actionFunction name="loadOpportunity" action="{!loadOpportunity}" immediate="true">
                    <apex:param name="p" assignTo="{!oppIdSelected}" value="" />
                    $(function() {
                        var cache = {},
                        $( ".autocompleteOpportunity" ).autocomplete({
                            //The loading of the list of opportunities is launched with at least 3 characters
                            minLength: 3,
                            //Loading the list of opportunities
                            source: function( request, response ) {
                                var term = request.term;
                                if ( term in cache ) {
                                    response( cache[ term ] );
                                lastXhr = SearchOpportunityController.getListOpportunity(request, function( data, status, xhr ) {
                                    cache[ term ] = data;
                                    if ( xhr === lastXhr ) {
                                        response( data );
                                }, {escape:true});
                            //Loading the opportunity from the item selected in the list
                            select: function( event, ui ) {
                <!-- Input text (hidden) to store the Opportunity id selected in the list -->
                <apex:inputText id="id_opp" value="{!oppIdSelected}" rendered="false"  />


 Apex controller "SearchOpportunityController"

public with sharing class SearchOpportunityController {
    * Inner class to create an JQueryUIAutoComplete wrapper.
    public class JQueryUIAutoCompleteWrapper {
        public String label {get; set;}
        public String id {get; set;}

        public JQueryUIAutoCompleteWrapper() {
            label = null;
            id = null;
    //Attributes used for the opportunity name autocomplete
    public String searchedCharacters{get;set;}
    public String oppIdSelected{get;set;}  
    //Attributes for the objects manipulated with the opportunity  
    public Opportunity myOpportunity{get;set;}      
    * Constructor.
    public SearchOpportunityController() {
        myOpportunity = new Opportunity();
    * Load the opportunity from the opportunity id selected.
    public void loadOpportunity() {
        Opportunity[] myOpportunities = [Select id, name from Opportunity where id =: oppIdSelected limit 1];
        myOpportunity = myOpportunities[0];
    * Action launch to return the list of opportunities matched from the input.
    public static List<JQueryUIAutoCompleteWrapper> getListOpportunity(String JSONString) {
        JQueryUIAutoCompleteWrapper[] listOpportunity = new List<JQueryUIAutoCompleteWrapper>();
        //Build JSON object from input
        JSONObject JSON = new JSONObject( JSONString );

        //Build searched pattern
        String searchedPattern = String.valueof(JSON.get('term')).trim() + '%';
        //Get list of matching opportunities id's and labels
        for(Opportunity oppName:[select id, Name from Opportunity where Name like :searchedPattern order by Name, id limit 10000]) {
            JQueryUIAutoCompleteWrapper oppW = new JQueryUIAutoCompleteWrapper();
            oppW.label = oppName.Name;
        return listOpportunity;








Finally after many tests, I think I found the solution.


The warning (error) popup message has clearly oriented myself to the use of the "global" keyword and I found some complements on the 2 following pages:


I'll let you know whether it works really well....




I feel a little bit alone ;-)


So for those who experience this problem, simply declare as global:
- The controller of the Visualforce
- The method declared in remote action


If it can help someone, you're welcome ;-)


Enjoy !

This was selected as the best answer

You rock @frelep!!




I have a solution for this - it turns out Remoting doesn't work within iframes. Since "Development Mode" uses iframes, you can't use a public remote method if development mode is turned on for your user.


Turning off dev mode works around the issue, although I think this is clearly a salesforce bug that needs fixing. 


thank you JamesAtCloudbuilders!!!

"clearly a salesforce bug that needs fixing" ... I completely agree.


Oh yeah, a bug to fix because current users like Sales for example should not have the "Developer mode" ;-)



Thanks!  Needed this big time.


Spot on.



I agree that this should be fixed. If I'm completely honest, I don't wish to turn my @RemoteAction method to global, especially since we cannot remove it afterwards.


I completely understand that the annotated method should only be used outside an iFrame, but this is within Salesforce's own iFrame. C'mon! :-)