加载大数据期间的ColdFusion和加载消息

时间:2019-08-09 11:23:01

标签: sql oracle coldfusion lazy-loading cfml

我有一个带有多个查询的cfm页面(一个查询的cfloop中有一个cfinvoke)。页面加载时,数据加载需要很长时间才能完全显示。

由于使用了cfloop,数据显示在html表中。我看到显示是逐步显示的。

我想知道如何通过延迟加载(带有加载消息或图标)来改善这一点。

我的脚本:

<!-------------------------------- GET DATA ON THE MEETING ----------------------------- START ---> 
<cftry>
    <cfquery name="qry_reunion" datasource="#application.datasource#">
        SELECT 
            R.*
        FROM REUNION R
        LEFT JOIN MODULES_V M on M.MOD_ID = R.I_MODULE_SIC_ID
        INNER JOIN APP_GEN_CODE_T B on B.ST_CODE = R.REUN_CNRE_ST_CODE  
        INNER JOIN APP_GEN_CODE_T D on d.ST_CODE = R.CSRE_ST_CODE
        where R.EXRC_NUMREXRC = '#form.year_source#'
        and B.ST_CLASS_CODE = 'BUD_CNRE'
        and d.ST_CLASS_CODE = 'BUD_CSRE' 
            <cfif #Searchstatut# is not "">
                and R.CSRE_ST_CODE = '#Searchstatut#'
            </cfif>
            <cfif #Searchnumber# is not "">
                and R.REUN_NUMREURO = '#Searchnumber#'
            </cfif>

        ORDER BY R.REUN_NUMRREUN    
    </cfquery>
    <cfcatch type="database">
        <!--- PUT THE VARIABLE errorDBquery TO 1 --> Disable the Save button of the form) --->
        <cfset SESSION.errorDBquery = 1>                                        
    </cfcatch>
</cftry>            
<!-------------------------------- GET DATA ON THE MEETING ------------------------------ END --->  

<cfset reunionIdList= "0" />


<cfif isdefined("qry_reunion.recordcount")> 
    <!--- Create the list of meeting number --->
    <cfloop from="1" to="#qry_reunion.recordcount#" index="i"> 
        <!--- create a var with all REUN_NUMRREUN used in this SCRIPT --->  
        <cfscript>
            reunionIdList &= ",";
            reunionIdList &= #qry_reunion.REUN_NUMRREUN[i]#;
        </cfscript>
    </cfloop>

    <cfif #qry_reunion.RECORDCOUNT# is 0 AND #searchorg# is not "">
        <br><br><cfoutput>#application.ui_lib_Result#</cfoutput>
    <cfelse>
        <br>
        <table class="dataTable">
            <thead>
                <cfoutput>
                <tr>
                    <th title="#application.ui_lib_numero#">#application.ui_lib_numero#</th>
                    <th title="#application.ui_lib_organisateur#">#application.ui_lib_organisateur#</th>
                    <th title="#application.ui_lib_objet#">#application.ui_lib_objet#</th>
                    <th title="#application.ui_lib_statut#">#application.ui_lib_statut#</th>
                    <th title="#application.ui_lib_ville#">#application.ui_lib_ville#</th>
                    <th title="">&nbsp;</th>
                </tr>
                </cfoutput>
            </thead>
            <tbody>     
                <!-------------------------------- Retrieve info on all unit  ------------------------------- START --->    
                <cfinvoke component="service/meetings" method="getMeetingsUnitLabel" returnvariable="meetingsUnit">
                    <cfinvokeargument name="meetingsNumber" value="#reunionIdList#">
                </cfinvoke>

                <cfloop from="1" to="#qry_reunion.recordcount#" index="i"> 
                    <cfoutput>

                    <form  action="reunion_status.cfm?mode=generalite_sta" method="post">
                        <tr>
                            <td class="cc">#qry_reunion.REUN_NUMREURO[i]#</td>
                            <td class="cc">

                                <!-------------------------------- Retrieve info on unit and check that the org_id is still active  ------------------------------- START --->  
                                <cfinvoke component="service/units" method="getUnitVersionFromMeetingOrgId" returnvariable="meetingUnitVersion">
                                    <cfinvokeargument name="meetingOrgId" value="#qry_reunion.ORG_ID[i]#"> 
                                    <cfinvokeargument name="meetingId" value="#qry_reunion.REUN_NUMRREUN[i]#"> 
                                    <cfinvokeargument name="unitsArray" value="#SerializeJSON(meetingsUnit.VALUES)#">                                   
                                </cfinvoke>


                                <cfif StructIsEmpty(meetingUnitVersion) eq false >
                                    <cfif #meetingUnitVersion.VALUES.OBSOLETE# EQ 0>
                                        <cfset unit ="#meetingUnitVersion.VALUES.ORG_CD#"/>
                                    <cfelse>
                                        <cfset unit ="#meetingUnitVersion.VALUES.ORG_CD# (obsolete)" />                                     
                                    </cfif>
                                    #unit#

                                    <cfif #meetingUnitVersion.VALUES.OBSOLETE# EQ 1 AND #meetingUnitVersion.VALUES.IS_ESTAT# eq 1>
                                        <!--- Dsiplay a tooltip when unit is archived --->
                                        <span id="obsoleteMeetingUnit_#i#" style="line-height:30px;">
                                                <img class='my-tooltip' src='pictures/questionmark.gif' style='vertical-align:middle;'>                 
                                        </span>                                             

                                        <cfset REUN_DATECREA = #DateFormat(qry_reunion.DATECREA[i], "dd/mm/yyyy")# />
                                        <script>
                                            var #toScript(meetingUnitVersion.VALUES.UNIT_VALID_FROM, "unitValidFrom")#; 
                                            var #toScript(meetingUnitVersion.VALUES.UNIT_VALID_TO, "unitValidTo")#; 
                                            var #toScript(meetingUnitVersion.VALUES.ORG_CD, "unitLabel")#;  
                                            var #toScript(REUN_DATECREA, "meetingCreationDate")#;   
                                            var #toScript(i, "i")#; 
                                                $("##obsoleteMeetingUnit_" +  i).tooltipster({
                                                    contentAsHTML: true,
                                                    interactive: true,              
                                                    animation: 'grow',
                                                    content: $("<span> was " + unitLabel + " <em>(valid from " + unitValidFrom + " to " + unitValidTo +")</em> when the meeting has been created on " + meetingCreationDate  +".</span>"),                                  
                                                    theme: 'tooltipster-shadow'         
                                                });                                             
                                        </script>   
                                    </cfif> 
                                <cfelse>
                                    Error
                                </cfif>
                            </td>
                            <td class="cc">#qry_reunion.REUN_OBJET[i]#</td>
                            <td class="cc">#qry_reunion.NATURE[i]#</td>
                            <td class="cc">#qry_reunion.VIL_CD[i]#</td>
                            <td class="cc">
                                <input type="hidden" name="REUN_NUMRREUN" value="#qry_reunion.REUN_NUMRREUN[i]#">
                                <input name="#application.ui_lib_chgt_status#" type="submit" value="#application.ui_lib_chgt_status#">
                            </td>
                        </tr>
                    </form>                 

                    </cfoutput>                                 

                </cfloop>   
            </tbody>
        </table>                            
    </cfif>

</cfif>

一些其他信息:

在我的数据库中,有一个所有单元的视图,其中包含当前信息和每个单元的历史记录。

会议链接到一个单元,但是该单元在视图中可以有多个记录。而且我需要获得链接到每个会议的单元的正确行

我需要根据在不同下拉列表中选择的过滤器来显示会议列表。

我创建了一个函数 getMeetingsUnitLabel ,用于从参数中的会议列表中获取所有单位的数据。它允许我将其用于1次或几次会议。

第二个功能 getUnitVersionFromMeetingOrgId 检索创建会议时使用的单位版本的正确记录(它使用从上一个功能中检索到的参数。

预先感谢您的帮助,

Seb

2 个答案:

答案 0 :(得分:2)

(评论太久了。)

第一件事:了解SQL injection(使用<cfqueryparam>)和DOM XSS(使用encodeForHtml())。您的页面上充满了漏洞,这与仅内部网/后台无关,因为安全性与每个地方都息息相关。

第二件事:了解何时使用#以及何时不需要它们。

最后:测量每个部分的性能。 getTickCount()可以为代码执行提供大致的时间增量(只是不要将其用于微基准测试)。通常,您要避免循环调用繁重的函数(请参见Big O notation),尤其是数据库/ IO调用。检索和处理数据一次,然后使用结果集,而不是为每个结果调用子函数。您没有告诉我们您的函数(getMeetingsUnitLabelgetUnitVersionFromMeetingOrgId)实际上是做什么的,也没有告诉您查询的性能,因此现在很难推荐任何特定的东西。

也:考虑将循环内的JavaScript块移至结尾处(循环之后)的单个脚本块。保持这种状态将比在表的每一行中四处乱动更容易。

答案 1 :(得分:2)

这里有很多东西。让我掩盖对我而言突出的内容。

使用cfoutput

...
            <cfloop from="1" to="#qry_reunion.recordcount#" index="i"> 
                <cfoutput>

...
                    <tr>
                        <td class="cc">#qry_reunion.REUN_NUMREURO[i]#</td>

...

是从数据库中获取数据的ColdFusion方法。看起来像其他语言一样。看起来应该真的是这样

...
                <cfoutput query="qry_reunion">

...
                    <tr>
                        <td class="cc">#REUN_NUMREURO#</td>

...

我工作过的某些地方真的很像对查询变量进行范围界定。那样的话

...
                <cfoutput query="qry_reunion">

...
                    <tr>
                        <td class="cc">#qry_reunion.REUN_NUMREURO#</td>

...

嵌套通话

  <cfloop
  ...
      <cfinvoke component="service/units" method="getUnitVersionFromMeetingOrgId" returnvariable="meetingUnitVersion">
      ... 

这只是要求缓慢。我将创建一个SQL用户定义的函数或一个视图来执行此操作。我想把数据收集工作放在数据库上,因为数据库比ColdFusion更了解收集,分组和联接数据

工具提示

  <span id="obsoleteMeetingUnit_#i#" style="line-height:30px;">
       <img class='my-tooltip' src='pictures/questionmark.gif' style='vertical-align:middle;'>                 
  </span>                                             
  ...
     var #toScript(i, "i")#; 
     $("##obsoleteMeetingUnit_" +  i).tooltipster({
                                                contentAsHTML: true,
                                                interactive: true,              
                                                animation: 'grow',
                                                content: $("<span> was " + unitLabel + " <em>(valid from " + unitValidFrom + " to " + unitValidTo +")</em> when the meeting has been created on " + meetingCreationDate  +".</span>"),                                  
                                                theme: 'tooltipster-shadow'         
                                            });                                             
                                    </script>

所有这些都是冗长的方式。更不用说互动可能真的很慢。如果您需要精美的工具提示。该模式应如下所示:

 <span class="custom_tooltip" 
    data-unitlabel     = "#EncodeForHTMLAttribute(unitLabel)#"
    data-unitvalidfrom = "#EncodeForHTMLAttribute(unitValidFrom)#"
    data-unitvalidto   = "#EncodeForHTMLAttribute(unitValidTo)#"
    data-dtCreate      = "#EncodeForHTMLAttribute(meetingCreationDate)#"
 ></span>

然后钩入一些document.ready的东西,并在所有内容加载完毕后应用工具提示的东西。

结论

生成的HTML数量大约是所需数量的两倍。所有这些都应该更小,更快。