"La raccolta Controlli non può essere modificata perché il controllo contiene blocchi di codice"


370

Sto cercando di creare un semplice controllo utente che è un dispositivo di scorrimento. Quando aggiungo un AjaxToolkit SliderExtender al controllo utente ottengo questo errore (* & $ # () @ #:

Server Error in '/' Application. The Controls collection cannot be modified because the control contains code blocks (i.e. `<% ... %>`). Description: An unhandled exception occurred during the execution of the current web request. Please review the stack trace for more information about the error and where it originated in the code.

Exception Details: System.Web.HttpException: The Controls collection cannot be modified because the control contains code blocks (i.e. `<% ... %>`).

Source Error:

An unhandled exception was generated during the execution of the current web request. Information regarding the origin and location of the exception can be identified using the exception stack trace below.

Stack Trace:

[HttpException (0x80004005): The Controls collection cannot be modified because the control contains code blocks (i.e. `<% ... %>`).]    System.Web.UI.ControlCollection.Add(Control child) +8677431    AjaxControlToolkit.ScriptObjectBuilder.RegisterCssReferences(Control control) in d:\E\AjaxTk-AjaxControlToolkit\Release\AjaxControlToolkit\ExtenderBase\ScriptObjectBuilder.cs:293 AjaxControlToolkit.ExtenderControlBase.OnLoad(EventArgs e) in d:\E\AjaxTk-AjaxControlToolkit\Release\AjaxControlToolkit\ExtenderBase\ExtenderControlBase.cs:306 System.Web.UI.Control.LoadRecursive()
+50    System.Web.UI.Control.LoadRecursive()
+141    System.Web.UI.Control.LoadRecursive()
+141    System.Web.UI.Control.LoadRecursive()
+141    System.Web.UI.Control.LoadRecursive()             
+141    System.Web.UI.Control.LoadRecursive()
+141    System.Web.UI.Control.LoadRecursive()
+141    System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint) +627


Version Information: Microsoft .NET Framework Version:2.0.50727.3074; ASP.NET Version:2.0.50727.3074

Ho provato a mettere un segnaposto nel controllo utente e ad aggiungere la casella di testo e l'estensione del dispositivo di scorrimento al segnaposto a livello di codice e continuo a ricevere l'errore.

Ecco il semplice codice:

<table cellpadding="0" cellspacing="0" style="width:100%">
    <tbody>
        <tr>
            <td></td>
            <td>
                <asp:Label ID="lblMaxValue" runat="server" Text="Maximum" CssClass="float_right" />
                <asp:Label ID="lblMinValue" runat="server" Text="Minimum" />
            </td>
        </tr>
        <tr>
            <td style="width:60%;">
                <asp:CheckBox ID="chkOn" runat="server" />
                <asp:Label ID="lblPrefix" runat="server" />:&nbsp;
                <asp:Label ID="lblSliderValue" runat="server" />&nbsp;
                <asp:Label ID="lblSuffix" runat="server" />
            </td>
            <td style="text-align:right;width:40%;">                

                    <asp:TextBox ID="txtSlider" runat="server" Text="50" style="display:none;" />
                    <ajaxToolkit:SliderExtender ID="seSlider" runat="server" 
                        BehaviorID="seSlider" 
                        TargetControlID="txtSlider" 
                        BoundControlID="lblSliderValue" 
                        Orientation="Horizontal" 
                        EnableHandleAnimation="true" 
                        Length="200" 
                        Minimum="0" 
                        Maximum="100" 
                        Steps="1" />

            </td>
        </tr>
    </tbody>
</table>

Qual è il problema?


11
Ciò che stava causando questo errore per me stava usando <% = Resolve (); %> all'interno dei tag <script> e <link>. Ho finalmente risolto questo problema. Invece di rimuovere il codice offensivo nel tag head che di solito causa questo errore. Inserisci semplicemente tutto il codice offensivo in un tag <asp: ContentPlaceHolder> </ asp: ContentPlaceHolder>.
Daniel P,

stackoverflow.com/questions/4995274/… Contiene una spiegazione più lunga per il @Daniel Psuggerimento.
lko,

Risposte:


498

Innanzitutto, avvia il blocco di codice con <% # anziché <% =:

<head id="head1" runat="server">
  <title>My Page</title>
  <link href="css/common.css" rel="stylesheet" type="text/css" />
  <script type="text/javascript" src="<%# ResolveUrl("~/javascript/leesUtils.js") %>"></script>
</head>

Ciò modifica il blocco di codice da un blocco di codice Response.Write a un'espressione di associazione dati.
Poiché le <%# ... %>espressioni di database non sono blocchi di codice, il CLR non si lamenterà. Quindi nel codice per la pagina principale, aggiungerebbe quanto segue:

protected void Page_Load(object sender, EventArgs e)
{
  Page.Header.DataBind();    
}

Non ricevo questo errore, ma sto usando la notazione =. Tuttavia: ho visto il mio codice fallire con il problema sopra descritto. Cosa può causare questo (del perché funziona bene con me)?
doekman,

3
Mi è sembrato di iniziare ad avere questo problema dopo essere passato ad ASP.NET 4. È isolato al nuovo framework?
Corgalore,

3
Viene risolto quando copio e incollo il mio codice Java Script nella parte inferiore della pagina. Nel precedente è stato inserito nel tag HEAD.
Miank,

1
Questo è un bug bizzarro con .NET. Perché #invece di =. Non lo capirò mai, lo faccio da anni ma vorrei sapere PERCHÉ!
Mark Pieszak - Trilon.io,

1
Eroi senza mantello se esistono!
Julián,

253

Ho riscontrato anche questo problema, ma ho trovato un'altra soluzione.

Ho scoperto che il wrapping dei blocchi di codice con un asp: PlaceHolder-tag risolve il problema.

<asp:PlaceHolder runat="server">
  <meta name="ROBOTS" content="<%= this.ViewData["RobotsMeta"] %>" />
</asp:PlaceHolder>

(Il CMS che sto usando si sta inserendo nella sezione head da parte di un codice dietro il quale mi ha impedito di aggiungere blocchi di controllo personalizzati con varie informazioni come meta-tag ecc, quindi questo è l'unico modo in cui funziona per me.)


11
Eccezionale. Come utente passato dei controlli di Telerik, usavo spesso il loro "RadCodeBlock" per lo stesso scopo, ma ero sempre infastidito dal fatto che non sapevo nulla oltre a quello (o come altri hanno già detto, spostando il codice in un tag creato per essere eseguito sul lato server). Non ho mai saputo che questi segnaposto potessero avere dei contenuti al loro interno. Grazie!
JayC,

1
Grazie in realtà a @JayC, RadCodeBlock è stato l'unico suggerimento in questa pagina che ha funzionato con il codice che ho ereditato, per vari motivi.
shiser,

Ciò si verifica anche con i controlli DevExpress registrati. Ho due applicazioni web con codice, configurazione e pagine master quasi identici. Solo quello con DevExpress richiede una soluzione come questa. Penso che abbia a che fare con il loro gestore HTTP, i gruppi di risorse o qualcosa del genere che rovina la pipeline. Ci stiamo allontanando dalle librerie di terze parti ora a favore di JQuery e MVC che consente di evitare gestori di codice / server lato server complessi.
Tony Wall,

In effetti è sufficiente avvolgerlo con <div runat = "server"> <% = (...)%> </div>
Zbigniew Wiadro,

5
@Teomanshipahi In realtà è piuttosto semplice: l'utilizzo di blocchi di codice all'interno di un contenitore significa che non è più possibile aggiornare Controlsquel contenitore. Questo sostanzialmente sfrutta questo comportamento inserendo il blocco di codice in un contenitore separato, quindi l'errore verrebbe visualizzato solo se si desidera modificare Controlsil controllo PlaceHolderanziché il controllo padre. PlaceHolderè un'ottima scelta per questo, perché non ha alcun codice proprio (a differenza, diciamo Panelo <div runat="server">). Anche se di solito lo uso al contrario, metti i controlli che devo modificare PlaceHolder.
Luaan,

55

Posso confermare che spostando il javascript con i <% %>tag dalla testa al tag del modulo si corregge questo errore

http://italez.wordpress.com/2010/06/22/ajaxcontroltoolkit-calendarextender-e-strana-eccezione/


1
Sì, appena confermato, la rimozione dei tag ASP <%%> dall'head risolve questo errore.
Corgalore,

+1, anche confermato. Per me, però, la sceneggiatura problematica era al di fuori sia della testa che degli elementi della forma.
user420667,

Confermato. Funziona come un incanto per me. Non dimenticare di controllare gli script sulla tua pagina principale poiché questo è stato quello che mi stava causando problemi e ho trascorso circa mezz'ora prima di capire che non era il mio aspx: P
Luis Hernández,

Sì, ha funzionato anche per me, ma perché? Il tag <HEAD> in un file Master è destinato esclusivamente al file Master e non ai file sub-aspx? Lo chiedo perché sto cercando di eseguire il codice JS in una pagina sub-aspx che risiede nel file principale.
Fandango68,

31

Posiziona il javascript sotto un tag div.

<div runat="server"> //div tag must have runat server
  //Your Jave script code goes here....
</div>

Funzionerà !!


5
O meglio, usa un segnaposto in modo che non venga generato alcun codice HTML aggiuntivo.
Chris Haines,

1
Funziona, anche se Visual Studio afferma che viola lo standard HTML5 per nidificare un <div> all'interno di un <head>.
Adi Inbar,

IMHO, non la migliore soluzione se HTML5 non viene convalidato, evitare div nella headsezione.
PreguntonCojoneroCabrón

8

puoi fare la stessa funzionalità se stai usando lo script manager nella tua pagina. devi solo registrare lo script in questo modo

<asp:ScriptManager ID="ScriptManager1" runat="server" LoadScriptsBeforeUI="true"   EnablePageMethods="true">  
<Scripts>
      <asp:ScriptReference Path="~/Styles/javascript/jquery.min.js" />
</Scripts>
</asp:ScriptManager>

ScriptManagernon aggiungere script nella sezione head ?
Kiquenet,

5

Ho avuto lo stesso problema nel controllo utente. La mia pagina che ospitava il controllo aveva commenti nel tag head, ho rimosso quei commenti, tutto ha funzionato in seguito. Alcuni post suggeriscono anche di rimuovere gli script dalla testa e di inserirli nel corpo.


5

Ho provato a usare <%# %>senza successo. Poi ho cambiato il Page.Header.DataBind();mio codice dietro a this.Header.DataBind();e ha funzionato bene.


4

Nel mio caso, ho sostituito <%= %>con <%# %>, e ha funzionato!


3

Mantenere il codice dello script java all'interno del tag body

<body> 
   <script type="text/javascript">
   </script>
</body>

2

La tecnica di databinding "<% #" non funzionerà direttamente all'interno dei tag <link> nel tag <head>:

<head runat="server">

  <link rel="stylesheet" type="text/css" 
        href="css/style.css?v=<%# My.Constants.CSS_VERSION %>" />

</head>

Il codice sopra verrà valutato

<head>

  <link rel="stylesheet" type="text/css" 
        href="css/style.css?v=&lt;%# My.Constants.CSS_VERSION %>" />

</head>

Invece, dovresti fare quanto segue (nota le due doppie virgolette all'interno):

<head runat="server">

  <link rel="stylesheet" type="text/css" 
        href="css/style.css?v=<%# "" + My.Constants.CSS_VERSION %>" />

</head>

E otterrai il risultato desiderato:

<head>

  <link rel="stylesheet" type="text/css" href="css/style.css?v=1.5" />

</head>

2

Ho avuto questo problema, ma non tramite l'intestazione. Il mio segnaposto era nel corpo. Così ho sostituito tutto il <%=con <%#e ha fatto

protected void Page_Load(object sender, EventArgs e)
{
    Page.Header.DataBind();    
}

e ha funzionato.


1

Un modo alternativo è far sì che un'altra pagina aspx funga da pagina a cui si desidera collegarsi.

Ecco come appare l'intestazione della Masterpage:

<head runat="server">
    <asp:ContentPlaceHolder ID="head" runat="server">
    </asp:ContentPlaceHolder>
    <link href="CSS/AccordionStyles.aspx" rel="stylesheet" type="text/css" />
</head>

Il modulo .aspx di riferimento contiene i tuoi contenuti:

<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="AccordionStyles.aspx.cs" Inherits="IntranetConnectCMS.CSS.AccordionStyles" %>
.AccordionHeader
{
    cursor: pointer;
    background-image: url(<%=ResolveUrl("~/Images/Backgrounds/AccordionPaneHeaderClosed.png") %>);
    background-repeat: no-repeat;
}

.AccordionHeaderSelected
{
    cursor: pointer;
    background-image: url(<%=ResolveUrl("~/Images/Backgrounds/AccordionPaneHeaderOpen.png") %>);
    background-repeat: no-repeat;
}
.AccordionContent
{
    background-image: url(<%=ResolveUrl("~/Images/Backgrounds/AccordionPaneContent.png") %>);
    background-repeat: no-repeat;
}

Infine, hai bisogno della pagina .aspx per dire al browser che stai inviando contenuto CSS:

protected void Page_Load(object sender, EventArgs e)
{
    Response.ContentType = "text/css";
}

1

Ho anche affrontato lo stesso problema. Ho trovato le soluzioni come segue.

Soluzione 1: ho mantenuto il mio tag script nel corpo.

<body>
   <form> . . . .  </form>
    <script type="text/javascript" src="<%= My.Working.Common.Util.GetSiteLocation()%>Scripts/Common.js"></script> </body>

Ora i conflitti relativi ai tag verranno risolti.

Soluzione 2:

Possiamo anche risolvere questa delle soluzioni precedenti come Sostituisci il blocco di codice con <% # anziché <% = Ma il problema è che fornirà solo il percorso relativo . Se vuoi un percorso davvero assoluto non funzionerà.

La soluzione 1 funziona per me. La prossima è la tua scelta.


1

Ho avuto lo stesso problema, ma non aveva nulla a che fare con JavaScript. Considera questo codice:

<input id="hdnTest" type="hidden" value='<%= hdnValue %>' />
<asp:PlaceHolder ID="phWrapper" runat="server"></asp:PlaceHolder>
<asp:PlaceHolder ID="phContent" runat="server" Visible="false">
    <b>test content</b>
</asp:PlaceHolder>

In questa situazione otterrai lo stesso errore anche se i PlaceHolder non hanno blocchi di codice dannosi, ciò accade a causa del controllo non server hdnTest utilizza blocchi di codice.

Aggiungi runat = server a hdnTest e il problema è risolto.


1

Ho risolto un errore simile a questo mettendo l' <script>interno contentplaceholderdentro <head>invece di mettere <script>fuori il detto contentplaceholderdentro<head>


1

Ho avuto lo stesso problema con circostanze diverse.
Avevo un semplice elemento all'interno del tag body.
La soluzione era:

<asp:PlaceHolder ID="container" runat="server">
    <a id="child" href="<%# variable %>">Change me</a>
</asp:PlaceHolder>
protected new void Page_Load(object sender, EventArgs e)
{    
    Page.Form.DataBind(); // I neded to Call DataBind on Form not on Header
    container.InnerHtml = "Simple text";
}

1

Ho avuto lo stesso problema con il mio sistema, ho rimosso il codice JavaScript dalla mia pagina e l'ho messo in corpo appena prima di chiudere il tag body


0

In alcuni casi ResolveUrl e ResolveClientUrl funzionano, ma non tutte le volte soprattutto in caso di file di script js. Quello che succede è che funziona per alcune pagine ma quando navighi verso altre pagine potrebbe non funzionare a causa del percorso relativo di quella particolare pagina.

Quindi, infine, il mio suggerimento è sempre di ricontrollare completamente le pagine del tuo sito per sapere se tutti i tuoi riferimenti javascript vanno bene o no. Apri il tuo sito in Google Chrome -> fai clic con il pulsante destro del mouse sulla pagina -> fai clic su Visualizza pagina di origine -> appare HTML -> ora fai clic sui tuoi collegamenti ipertestuali JS; se funziona bene dovrebbe aprire il file js in un'altra finestra del browser, altrimenti non si aprirà.


0

Prova a scrivere il tuo codice java script al di fuori del tag head, funzionerà sicuramente. Si risolve quando copio e incollo il mio codice Java Script nella parte inferiore della pagina. Nel precedente è stato inserito nel tag HEAD ora appena prima di chiudere il tag del modulo.

    </div>
        <script>
                    function validate() {
                        try {

                        var username = document.getElementById("<%=txtUserName.ClientID%>").value;
                        var password = document.getElementById("<%=txtPWD.ClientID%>").value;

                            if (username == "" && password == "")
                                alert("Enter Username and Passowrd");
                            else {
                                if (username == "")
                                    alert("Enter Username");
                                else if (password == "")
                                    alert("Enter Password");
                            }

                        }

                    catch (err) {
                    }
                }
                </script>
</form>

0

Rimuovere la parte che ha i tag del server e posizionarla altrove se si desidera aggiungere controlli dinamici dal codice sottostante

Ho rimosso il mio JavaScript dalla sezione head della pagina e l'ho aggiunto al corpo della pagina e l'ho fatto funzionare


0

Nel mio caso ho riscontrato questo errore perché stavo impostando erroneamente InnerText su un div con HTML all'interno.

Esempio:

SuccessMessagesContainer.InnerText = "";

   <div class="SuccessMessages ui-state-success" style="height: 25px; display: none;" id="SuccessMessagesContainer" runat="server">
      <table>
         <tr>
            <td style="width: 80px; vertical-align: middle; height: 18px; text-align: center;">
               <img src="<%=Image_success_icn %>" style="margin: 0 auto; height: 18px;
                  width: 18px;" />
            </td>
            <td id="SuccessMessage" style="vertical-align: middle;" class="SuccessMessage" runat="server" >
            </td>
         </tr>
      </table>
   </div>

-1

I tag <%= %>non funzionano in un tag con runat="server". Spostare il codice con <%= %>in runat="server"un altro tag ( body, head, ...), o rimuovere runat="server"dal contenitore.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.