Hello!
Today we encountered an error with our application after moving it to a new machine with different resources available to it. According to the cursory research I have done, it looks like the machine has run out of memory for the app to use. This is the error message that was printed to the screen:
Now, I did some testing after moving back to working in my local development environment. It looks like every time I refresh the app’s homepage, it adds about 2 megabytes of memory used.
Before a lot of refreshes:
After a lot of refreshes:
My next course of action was to take a look at any of the variables or objects that might be declared by requesting this page. So, here’s the handler, layout, and view.
Handler:
I should note here, that some of the models injected here also inject one another in their own cfcs.
component {
//Modules/Models
property name = "messageBox" inject="messageBox@cbmessagebox";
property name = "mainHelper" inject="mainHelper";
property name = "sessionsHelper" inject="sessionsHelper";
property name = "userService" inject="userService";
property name = "formManagerHelper" inject="formManagerHelper";
property name = "automailer" inject="automailer";
property name = "auth" inject="authenticationService@cbauth";
/**
* Sets the view to the root of the web application
*/
function index( event, rc, prc )
{
event.paramvalue("msg","");
//These are some messages that could pop up in the index
if(rc.msg == "invalidAuth")
{
messageBox.warn("It looks like you aren't authorized to do that!");
}
else if(rc.msg == "invalidShareToken")
{
messageBox.warn("This sharing link has expired or is invalid. Please get a new share link for this form.");
}
else if(rc.msg == "invalidAccessRequest")
{
messagebox.warn("The share link you tried to access had an invalid access type it tried to share with you.");
}
else if(rc.msg != "")
{
messagebox.warn("It looks like an error occurred: " & rc.msg);
}
//Obtain all of the names of the forms so they can be displayed on the front page
rc.publishedForms = mainHelper.getPublishedForms();
//Obtain the names of the top 4 most submitted forms
rc.mostSubmittedForms = mainHelper.getMostSubmittedForms();
event.setView( "main/index" );
}
.
.
.
}
Layout:
<cfscript>
variables.cbSession = new modules.cbstorages.models.SessionStorage(); //Instantiate cbStorages for Session
</cfscript>
<cfoutput>
<!DOCTYPE HTML>
<html lang="en">
<head>
<!-- Required meta tags -->
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
<title>Loeb Electric Forms</title>
<meta name="description" content="Loeb Electric Application Template">
<meta name="author" content="Ortus Solutions, Corp">
<!---Base URL --->
<base href="#event.getHTMLBaseURL()#" />
<!--- Load up bootstrap from local installation--->
<link rel="stylesheet" href="includes/bootstrap-5.1.3-dist/css/bootstrap.css">
<!--- Load jquery using CDN --->
<script src="./includes/javascript/jquery-3.6.1.min.js"></script>
<!--- Load intlTelInput --->
<link
rel="stylesheet"
href="https://cdnjs.cloudflare.com/ajax/libs/intl-tel-input/17.0.8/css/intlTelInput.css"
/>
<script src="https://cdnjs.cloudflare.com/ajax/libs/intl-tel-input/17.0.8/js/intlTelInput.min.js"></script>
<!--- Load up style sheets for independent objects --->
<link rel="stylesheet" href="includes/styles/switches.css">
<link rel="stylesheet" href="includes/styles/specialButtons.css">
<link rel="stylesheet" href="includes/styles/formattingUtilities.css">
<link rel="stylesheet" href="includes/styles/pagination.css">
<link rel="stylesheet" href="includes/styles/header.css">
<link rel="stylesheet" href="includes/styles/footer.css">
<link rel="stylesheet" href="includes/styles/formElements.css">
<link rel="stylesheet" href="includes/styles/fileInputs.css">
<link rel="stylesheet" href="includes/styles/formManager.css">
<!--- Custom CSS, check for lightTheme or darkTheme setting --->
<cfif "#variables.cbSession.exists("user")#">
<cfif "#variables.cbSession.get("user").getSettings().theme#" == "lightTheme">
<!--- If we are logged in and have opted for the light theme, show the light theme! --->
<link rel="stylesheet" href="./includes/styles/baseStylesLight.css">
<!--- Datatables light theme --->
<link rel="stylesheet" type="text/css" href="./includes/DataTables/datatablesLight.css"/>
<cfelseif "#variables.cbSession.get("user").getSettings().theme#" == "darkTheme">
<!--- If we have opted for the dark theme instead, show that! --->
<link rel="stylesheet" href="./includes/styles/baseStylesDark.css">
<!--- Datatables dark theme --->
<link rel="stylesheet" type="text/css" href="./includes/DataTables/datatablesDark.css"/>
</cfif>
<cfelse>
<!--- If we aren't logged in, use light theme by default --->
<link rel="stylesheet" href="./includes/styles/baseStylesLight.css">
<link rel="stylesheet" type="text/css" href="./includes/DataTables/datatablesLight.css"/>
<!--- <script src="https://kit.fontawesome.com/a076d05399.js" crossorigin="anonymous"></script> --->
</cfif>
<script type="text/javascript" src="./includes/DataTables/datatables.min.js"></script>
</head>
<body data-spy="scroll" data-target=".navbar" data-offset="50" style="padding-top: 0px">
<!---Top NavBar --->
<header id="baseHeader" role="Header">
<div id="logoWrapper" class="wrapper">
<!---Brand: show logo for either light or dark theme --->
<cfif "#variables.cbSession.exists("user")#">
<cfif "#variables.cbSession.get("user").getSettings().theme#" == "lightTheme">
<a href="#event.buildLink("")#">
<img class="rounded mx-auto d-block" width="150" src="includes/images/loeb-electric-logo.png" alt="logo" id ="logo"/>
</a>
<cfelseif "#variables.cbSession.get("user").getSettings().theme#" == "darkTheme">
<a href="#event.buildLink("")#">
<img class="rounded mx-auto d-block" width="150" src="includes/images/loeb-electric-logo-DARKTHEME.png" alt="logo" id="logo"/>
</a>
</cfif>
<cfelse>
<a href="#event.buildLink("")#">
<img class="rounded mx-auto d-block" width="150" src="includes/images/loeb-electric-logo.png" alt="logo" id="logo"/>
</a>
</cfif>
</div>
<div id="headerNav">
<div id="navWrapper">
<nav id="mainNav">
<div class="navbarItem">
<a href="#event.buildLink('')#">
<button class="btn navbarBtn">
Home
</button>
</a>
</div>
<div class="navbarItem">
<a href="#event.buildLink('formManager.index')#">
<button class="btn navbarBtn">
Manage forms
</button>
</a>
</div>
</nav>
</div>
</div>
</header>
<!---end navbar --->
<!--- <cfscript>
writeDump(session)
</cfscript> --->
<!---This is messagebox!--->
<div id="messagebox">#getInstance("messagebox@cbMessageBox").renderit()#</div>
<!---Container for views --->
<div id="view" class="container-full-width" >#renderView()#</div>
<footer align="center">
<br/>
Copyright Loeb Electric, Inc 2023. All rights reserved.
<br/>
<a href="https://loebelectric.com/privacy-policy/">Privacy Policy</a> |
<a href="https://loebelectric.com/terms-of-use/">Terms of Use</a> |
<a href="https://loebelectric.com/wp-content/uploads/2020/06/Standard_Terms_and_Conditions.pdf">Terms and Conditions</a> |
<a href="https://pastebin.com/AfjbMQrx">Attribution of resources</a>
</footer>
<!---js --->
<!-- Bootstrap requirements: -->
<!--- <script src="./includes/javascript/popper.min.js"></script> --->
<script src="./includes/bootstrap-5.1.3-dist/js/bootstrap.bundle.min.js"></script>
<!-------------------------------->
<script>
$(function() {
// activate all drop downs
$('.dropdown-toggle').dropdown();
// Tooltips
$("[rel=tooltip]").tooltip();
})
</script>
</body>
</html>
</cfoutput>
View:
<cfoutput>
<!---
This is the main landing page and root of the site.
--->
<!DOCTYPE html>
<html>
<head>
<title>Home</title>
</head>
<body>
<cfif auth().isLoggedIn() AND !rc.keyExists("searchForms")>
<div class="viewHeader">
<h1 align="center">User Homepage</h1>
</div>
<!--- Show some buttons for logged in users --->
<div id="menuView" class="container" align="center">
<div class="row justify-content-center">
<!---Search forms--->
<div class="col-md-auto">
<a href="#event.buildLink("?searchForms=true")#">
<button type="button" id="button1" class="btn btn-primary dashboard-icon" data-line="true">
<img src="./includes/images/noun-magnifier.png" width="70px" height="70px">
<br>
Search forms
</button>
</a>
</div>
<!---Manage forms--->
<div class="col-md-auto">
<a href="#event.buildLink("formManager.index")#">
<button type="button" id="button1" class="btn btn-primary dashboard-icon" data-line="true">
<img src="./includes/images/noun-form.png" width="70px" height="70px">
<br>
Manage forms
</button>
</a>
</div>
<!---User dashbaord--->
<cfif listContains(auth().getUser().getPermissions(),"user")>
<div class="col-md-auto">
<a href="#event.buildLink(to = "user-dashboard.index", queryString = "menu=account-information")#">
<button type="button" id="button1" class="btn btn-primary dashboard-icon" data-line="true">
<img src="./includes/images/noun-user.png" width="70px" height="70px">
<br>
User dashboard
</button>
</a>
</div>
</cfif>
</div>
<br>
<div class="row justify-content-center" align="center">
<!---Row 2 of dashboard icons--->
<!---Show the button for the admin dashboard only to admins --->
<cfif listContains(auth().getUser().getPermissions(),"admin")>
<div class="col-md-auto">
<a href="#event.buildLink("admin-dashboard")#">
<button type="button" id="button1" class="btn btn-primary dashboard-icon" data-line="true">
<img src="./includes/images/noun-admin.png" width="70px" height="70px">
<br>
Admin dashboard
</button>
</a>
</div>
</cfif>
<!---Logout--->
<div class="col-md-auto">
<form method="POST" action="#event.buildLink("logout")#">
<input type="hidden" name="_method" value="DELETE" />
<button type="submit" id="button1" class="btn btn-primary dashboard-icon" data-line="true">
<img src="./includes/images/noun-logout.png" width="70px" height="70px">
<br>
Logout
</button>
</form>
</div>
</div>
<br>
<div class="row justify-content-center" align="center">
<!---Row 3 of dashboard icons--->
<div class="col-md-auto">
</div>
<div class="col-md-auto">
</div>
<div class="col-md-auto">
</div>
</div>
</div>
<cfelse>
<!--- Show the options for users who are NOT logged in or who just want to look at forms --->
<div class="viewHeader" align="center">
<h1 align="center">Loeb Electric Forms</h1>
</div>
<cfif rc.publishedForms.recordCount() GT 0>
<p id="homepageInstructionText" align="center">Search or select a form below</p>
<div class="container" align="center">
<div id="formSelectDataTableBackground" class="datatableBackground" style="width : 75%">
<!----
Use datatables
----->
<script>
$(document).ready( function () {
$('##formSearchTable').DataTable(
{
}
);
} );
</script>
<!---------------------->
<table id="formSearchTable" class="cell-border row-border compact stripe order-column">
<thead>
<tr>
<th>Form</th>
<th>Description</th>
</tr>
</thead>
<tbody>
<cfloop index="i" from="1" to="#rc.publishedForms.recordCount()#">
<tr>
<td>
<a href="#event.buildLink("main.fillout?formPK=" & rc.publishedForms.getRow(i)["FormPK"])#">
<button class="openFormButton-datatable">
<span>#rc.publishedForms.getRow(i)["Name"]#</span>
</button>
</a>
</td>
<td>
#rc.publishedForms.getRow(i)["Description"]#
</td>
</tr>
</cfloop>
</tbody>
</table>
</div>
<cfif rc.mostSubmittedForms.len() GT 0>
<br>
<h2>Popular forms</h2>
<br>
<!---
Show the popular forms. First, we show all of the forms that have the highest number of
submissions (up to 5). If there only a few forms with submissions, we then show the next
available forms that have no submissions
--->
<cfset formButtonNumber = 1>
<cfloop index="r" from="1" to="3">
<div class="row g-0 justify-content-center">
<cfloop index="c" from="1" to="3">
<cfif formButtonNumber LTE rc.mostSubmittedForms.len()>
<div class="col-4">
<a href="#event.buildLink("main.fillout?formPK=" & rc.mostSubmittedForms[formButtonNumber]["formPK"])#">
<button class="openFormButton">
#rc.mostSubmittedForms[formButtonNumber]["formName"]#
</button>
</a>
<cfset formButtonNumber = formButtonNumber + 1>
</div>
</cfif>
</cfloop>
</div>
<br/>
</cfloop>
</cfif>
</div>
<cfelse>
<p id="homepageInstructionText" align="center">Sorry, there are currently no forms available.</p>
</cfif>
<!--- Homepage buttons for registration and login, respectively --->
<div align="center">
<!--- Login with either a loeb account or a microsoft accoount w/sso --->
</div>
</cfif>
</body>
</html>
</cfoutput>
So my question to the community is, am I on the right track? Should I be looking to find instances of where models/modules/variables are declared more than they need to be if I keep adding memory usage every time the page is hit?
In addition, can anyone spot an error I’m making with the addition of more and more memory? It might have something to do with wirebox which I am not well-versed in.