“ คอลเลกชันตัวควบคุมไม่สามารถแก้ไขได้เนื่องจากตัวควบคุมประกอบด้วยบล็อครหัส”


370

ฉันพยายามสร้างตัวควบคุมผู้ใช้อย่างง่ายที่เป็นตัวเลื่อน เมื่อฉันเพิ่ม AjaxToolkit SliderExtender ในการควบคุมผู้ใช้ฉันได้รับข้อผิดพลาด (* & $ # () @ # นี้:

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

ฉันลองวางตัวแทนในการควบคุมของผู้ใช้และเพิ่มกล่องข้อความและตัวเลื่อนส่วนขยายไปยังตัวยึดตำแหน่งโดยทางโปรแกรมและฉันยังคงได้รับข้อผิดพลาด

นี่คือรหัสง่าย ๆ :

<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>

อะไรคือปัญหา?


11
สิ่งที่ทำให้เกิดข้อผิดพลาดนี้สำหรับฉันคือการใช้ <% = Resolve (); ฟังก์ชั่น%> ภายในแท็ก <script> และ <link> ในที่สุดฉันก็แก้ไขสิ่งนี้ แทนที่จะลบรหัสที่กระทำผิดในแท็กส่วนหัวที่มักทำให้เกิดข้อผิดพลาดนี้ เพียงใส่รหัสที่ละเมิดทั้งหมดลงในแท็ก <asp: ContentPlaceHolder> </ asp: ContentPlaceHolder>
Daniel P

stackoverflow.com/questions/4995274/…มีคำอธิบายเพิ่มเติมสำหรับ@Daniel Pคำแนะนำ
lko

คำตอบ:


498

ก่อนอื่นให้เริ่มบล็อกโค้ดด้วย <% # แทนที่จะเป็น <% =:

<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>

สิ่งนี้จะเปลี่ยนบล็อกรหัสจากการบล็อกรหัส Response.Write เป็นนิพจน์ databinding
เนื่องจาก<%# ... %>นิพจน์ databinding ไม่ใช่บล็อคโค้ด CLR จึงไม่บ่น จากนั้นในโค้ดสำหรับหน้าต้นแบบคุณจะต้องเพิ่มสิ่งต่อไปนี้:

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

ฉันไม่ได้รับข้อผิดพลาดนี้ แต่ฉันใช้เครื่องหมาย = อย่างไรก็ตาม: ฉันเห็นรหัสของฉันล้มเหลวด้วยปัญหาที่อธิบายไว้ข้างต้น อะไรทำให้เกิดสิ่งนั้น (เพราะเหตุใดมันถึงใช้ได้กับฉัน)
doekman

3
ฉันดูเหมือนจะเริ่มมีปัญหานี้หลังจากเปลี่ยนเป็น ASP.NET 4 มันแยกกับกรอบใหม่หรือไม่?
Corgalore

3
แก้ไขได้เมื่อฉันคัดลอกและวางโค้ด Java Script ของฉันไปที่ด้านล่างของหน้า ก่อนหน้านี้วางไว้ในแท็ก HEAD
Miank

1
นี่เป็นข้อผิดพลาดที่แปลกประหลาดกับ. NET ทำไมแทน# =ฉันจะไม่เข้าใจคนนี้ทำมาหลายปีแล้ว แต่หวังว่าฉันจะรู้ว่าทำไม!
Mark Pieszak - Trilon.io

1
วีรบุรุษไร้เสื้อคลุมหากพวกเขามีอยู่!
Julián

253

ฉันเพิ่งพบปัญหานี้เช่นกัน แต่พบวิธีแก้ไขปัญหาอื่น

ฉันพบว่าการตัดบล็อคโค้ดด้วย asp: PlaceHolder-tag ช่วยแก้ปัญหา

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

(CMS ที่ฉันใช้กำลังแทรกลงในส่วนหัวจากโค้ดบางอันซึ่ง จำกัด ฉันไม่ให้เพิ่มบล็อกควบคุมแบบกำหนดเองที่มีข้อมูลต่าง ๆ เช่นเมตาแท็ก ฯลฯ ดังนั้นนี่เป็นวิธีเดียวที่เหมาะกับฉัน)


11
น่ากลัว ในฐานะผู้ใช้ที่ผ่านมาของตัวควบคุม Telerik ฉันมักจะใช้ "RadCodeBlock" ของพวกเขาเพื่อจุดประสงค์เดียวกัน แต่มักจะรู้สึกรำคาญกับความจริงที่ว่าฉันไม่รู้อะไรเลยนอกจากนั้น (หรืออย่างที่คนอื่น ๆ พูดถึง แท็กที่สร้างขึ้นเพื่อเรียกใช้ฝั่งเซิร์ฟเวอร์) ฉันไม่เคยรู้ว่าตัวแทนเหล่านี้สามารถมีเนื้อหาภายในได้ ขอบคุณ!
JayC

1
ขอบคุณ @JayC จริง RadCodeBlock เป็นข้อเสนอแนะเพียงอย่างเดียวในหน้านี้ที่ทำงานกับรหัสที่ฉันสืบทอดมาด้วยเหตุผลหลายประการ
shiser

นอกจากนี้ยังเกิดขึ้นกับการควบคุม DevExpress ที่ลงทะเบียน ฉันมีเว็บแอพพลิเคชั่นสองตัวที่มีรหัสการกำหนดค่าและหน้าต้นแบบเกือบเหมือนกัน เฉพาะคนที่มี DevExpress เท่านั้นที่ต้องมีวิธีแก้ไขเช่นนี้ ฉันคิดว่ามันเป็นสิ่งที่ต้องทำกับตัวจัดการ HTTP ของพวกเขาประกอบทรัพยากรหรือสิ่งที่คล้ายกันที่ทำให้ท่อไป เราย้ายออกจากไลบรารี่ของบุคคลที่สามในขณะนี้เพื่อสนับสนุน JQuery และ MVC ซึ่งช่วยให้คุณหลีกเลี่ยงโค้ด / ตัวจัดการฝั่งเซิร์ฟเวอร์ที่ซับซ้อน
Tony Wall

ในความเป็นจริงมันเพียงพอที่จะหุ้มด้วย <div runat = "server"> <% = (... )%> </div>
Zbigniew Wiadro

5
@Teomanshipahi จริงๆแล้วมันค่อนข้างง่าย - การใช้บล็อคโค้ดในคอนเทนเนอร์หมายความว่าคุณจะไม่สามารถอัปเดตControlsคอนเทนเนอร์นั้นได้อีกต่อไป สิ่งนี้โดยทั่วไปจะใช้ประโยชน์จากพฤติกรรมนี้โดยวางบล็อกโค้ดไว้ในที่เก็บแยกต่างหากดังนั้นข้อผิดพลาดจะปรากฏขึ้นเฉพาะในกรณีที่คุณต้องการแก้ไขControlsของPlaceHolderแทนที่จะเป็นคอนโทรลพาเรนต์ PlaceHolderเป็นตัวเลือกที่ยอดเยี่ยมสำหรับสิ่งนี้เนื่องจากไม่มีรหัสของตัวเอง (ต่างจากพูดPanelหรือ<div runat="server">) ถึงแม้ว่าผมมักจะใช้วิธีอื่น ๆ - PlaceHolderใส่การควบคุมที่ฉันจำเป็นต้องปรับเปลี่ยนใน
Luaan

55

ฉันสามารถยืนยันได้ว่าการย้ายจาวาสคริปต์ด้วย<% %>แท็กจากส่วนหัวไปยังแท็กฟอร์มแก้ไขข้อผิดพลาดนี้

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


1
ใช่เพิ่งยืนยันลบแท็ก ASP <%%> ออกจากส่วนหัวแก้ไขข้อผิดพลาดนี้
Corgalore

+1 ได้รับการยืนยันเช่นกัน สำหรับฉันแม้ว่าสคริปต์ที่มีปัญหานั้นอยู่นอกองค์ประกอบทั้งส่วนหัวและแบบฟอร์ม
user420667

ได้รับการยืนยัน ทำงานเหมือนจับใจสำหรับฉัน อย่าลืมตรวจสอบสคริปต์ในหน้าต้นแบบของคุณเนื่องจากนี่เป็นสาเหตุที่ทำให้ฉันมีปัญหาและฉันใช้เวลาครึ่งชั่วโมงก่อนที่จะทราบว่าไม่ใช่ aspx ของฉัน: P
Luis Hernández

ใช่มันใช้ได้กับฉันด้วย แต่ทำไม? แท็ก <HEAD> ในไฟล์ Master นั้นมีความหมายสำหรับไฟล์ Master อย่างแท้จริงและไม่มีไฟล์ย่อย aspx หรือไม่ ฉันถามเพราะฉันพยายามเรียกใช้รหัส JS ในหน้าย่อย aspx ที่อยู่ในไฟล์ต้นแบบ
Fandango68

31

วางจาวาสคริปต์ไว้ใต้แท็ก div

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

มันจะทำงาน !!


5
หรือดีกว่าใช้ตัวยึดตำแหน่งเพื่อไม่ให้มีการส่งรหัส html เพิ่มเติม
Chris Haines

1
ใช้งานได้แม้ว่า Visual Studio จะบอกว่าเป็นการละเมิดมาตรฐาน HTML5 เพื่อซ้อน <div> ภายใน <head>
Adi Inbar

IMHO ไม่ใช่วิธีแก้ปัญหาที่ดีที่สุดหาก HTML5 ไม่ได้ตรวจสอบความถูกต้องหลีกเลี่ยงdivในheadส่วน
PreguntonCojoneroCabrón

8

คุณสามารถใช้ฟังก์ชันการทำงานเดียวกันได้หากคุณใช้โปรแกรมจัดการสคริปต์ในหน้าเว็บของคุณ คุณต้องลงทะเบียนสคริปต์เช่นนี้

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

ScriptManagerไม่เพิ่มสคริปต์ในส่วนหัว ?
Kiquenet

5

ฉันมีปัญหาเดียวกันในการควบคุมผู้ใช้ หน้าของฉันที่ถูกโฮสต์การควบคุมมีความคิดเห็นในแท็กหัวฉันลบความคิดเห็นเหล่านั้นทุกอย่างทำงานหลังจากนั้น บางโพสต์ยังแนะนำให้ลบสคริปต์จากหัวและวางไว้ในเนื้อหา


5

ฉันลองใช้โดย<%# %>ไม่ประสบความสำเร็จ จากนั้นฉันก็เปลี่ยนPage.Header.DataBind();รหัสของฉันไปthis.Header.DataBind();และมันก็ใช้ได้ดี




2

เทคนิคการจัดทำข้อมูล "<% #" จะไม่สามารถทำงานได้โดยตรงภายในแท็ก <link> ในแท็ก <head>:

<head runat="server">

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

</head>

โค้ดด้านบนจะถูกประเมินเป็น

<head>

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

</head>

คุณควรทำสิ่งต่อไปนี้แทน (ให้สังเกตเครื่องหมายอัญประกาศคู่ด้านใน):

<head runat="server">

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

</head>

และคุณจะได้รับผลลัพธ์ที่ต้องการ:

<head>

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

</head>

2

ฉันมีปัญหานี้ แต่ไม่ผ่านส่วนหัว ตัวยึดตำแหน่งของฉันอยู่ในร่างกาย ดังนั้นฉันจึงแทนที่ทั้งหมด<%=ด้วย<%#และทำ

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

และมันก็ใช้งานได้


1

อีกทางเลือกหนึ่งคือให้เพจ. aspx อื่นทำหน้าที่เป็นเพจที่คุณต้องการเชื่อมโยง

นี่คือลักษณะที่ส่วนหัวของมาสเตอร์เพจ:

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

แบบฟอร์ม. aspx ที่อ้างอิงมีเนื้อหาของคุณ:

<%@ 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;
}

สุดท้ายคุณต้องมีหน้า. aspx เพื่อบอกเบราว์เซอร์ที่คุณส่งเนื้อหา CSS:

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

1

ฉันยังต้องเผชิญกับปัญหาเดียวกัน ฉันพบวิธีแก้ปัญหาดังต่อไปนี้

โซลูชันที่ 1: ฉันเก็บแท็กสคริปต์ไว้ในเนื้อหา

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

ตอนนี้ความขัดแย้งเกี่ยวกับแท็กจะแก้ไขได้

โซลูชันที่ 2:

นอกจากนี้เรายังสามารถแก้ปัญหาหนึ่งของการแก้ปัญหาดังกล่าวข้างต้นเช่นนี้แทนที่การป้องกันรหัสที่มี <% # แทน <% =แต่ปัญหาคือมันจะให้เฉพาะทางญาติ หากคุณต้องการเส้นทางที่สมบูรณ์จริงๆมันจะไม่ทำงาน

โซลูชันที่ 1 ใช้ได้สำหรับฉัน ถัดไปเป็นทางเลือกของคุณ


1

ฉันมีปัญหาเดียวกัน แต่ไม่มีอะไรเกี่ยวข้องกับ JavaScript พิจารณารหัสนี้:

<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>

ในสถานการณ์เช่นนี้คุณจะได้รับข้อผิดพลาดเดียวกันแม้ว่า PlaceHolders จะไม่มีบล็อคโค้ดที่เป็นอันตราย แต่เกิดขึ้นเนื่องจาก hdnTest ที่ไม่ใช่เซิร์ฟเวอร์ควบคุมใช้บล็อคโค้ด

เพียงแค่เพิ่ม runat = server ใน hdnTest และแก้ไขปัญหา


1

ฉันแก้ไขข้อผิดพลาดแบบนี้โดยการใส่<script>ข้างcontentplaceholderใน<head>แทนการใส่<script>ข้างในcontentplaceholderข้างใน<head>


1

ฉันมีปัญหาเดียวกันกับสถานการณ์ที่แตกต่างกัน
ฉันมีองค์ประกอบง่ายๆภายในแท็กร่างกาย
ทางออกคือ:

<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

ฉันมีปัญหาเดียวกันกับระบบของฉันฉันลบรหัส JavaScript ออกจากหน้าของฉันและวางไว้ที่เนื้อหาก่อนปิดแท็กเนื้อหา


0

สำหรับบางกรณี ResolveUrl และ ResolveClientUrl ทำงานได้ แต่บางครั้งโดยเฉพาะในกรณีของไฟล์สคริปต์ js จะเกิดอะไรขึ้นสำหรับบางหน้า แต่เมื่อคุณนำทางไปยังหน้าอื่น ๆ อาจไม่ทำงานเนื่องจากเส้นทางสัมพัทธ์ของหน้านั้น ๆ

ดังนั้นในที่สุดข้อเสนอแนะของฉันจะทำการตรวจสอบหน้าเว็บไซต์ของคุณอีกครั้งว่าการอ้างอิงจาวาสคริปต์ทั้งหมดของคุณนั้นดีหรือไม่ เปิดไซต์ของคุณใน Google Chrome -> คลิกขวาที่หน้า -> คลิกดูหน้าแหล่งที่มา -> HTML ปรากฏ -> ตอนนี้คลิกที่ไฮเปอร์ลิงก์ JS ของคุณ หากทำงานได้ดีก็ควรเปิดไฟล์ js ในหน้าต่างเบราว์เซอร์อื่นมิฉะนั้นจะไม่เปิด


0

ลองเขียนโค้ดจาวาสคริปต์ของคุณนอกแท็กส่วนหัวมันจะใช้งานได้แน่นอนแก้ไขเมื่อฉันคัดลอกและวางโค้ดจาวาสคริปต์ของฉันที่ด้านล่างของหน้า ก่อนหน้านี้วางไว้ในแท็ก HEAD ทันทีก่อนที่จะปิดแท็กแบบฟอร์ม

    </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

ลบส่วนที่มีแท็กเซิร์ฟเวอร์และวางไว้ที่อื่นถ้าคุณต้องการเพิ่มการควบคุมแบบไดนามิกจากโค้ดด้านหลัง

ฉันลบ JavaScript ของฉันออกจากส่วนหัวของหน้าและเพิ่มลงในเนื้อความของหน้าและทำให้มันใช้งานได้


0

ในกรณีของฉันฉันได้รับข้อผิดพลาดนี้เนื่องจากฉันตั้งค่า InnerText เป็น div ด้วย html ภายใน

ตัวอย่าง:

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

แท็กไม่ทำงานลงในแท็กด้วย<%= %> runat="server"ย้ายโค้ดของคุณด้วยการ<%= %>เข้าไปในrunat="server"ที่จะแท็กอื่น ๆ ( body, head... ) หรือลบrunat="server"จากตู้คอนเทนเนอร์

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.