How to display each element in a ColdFusion query - coldfusion

I have written this piece of CF code to get and display the data from database. (Actually to populate text fields.) The problem: I am not getting values from the query, but I am correctly getting the number of records.
How am I supposed to access the values returned by the query via a cfloop? Below is my work.
<cfquery name="data_query" datasource="#dsn#">
SELECT
id,
name
FROM learning
</cfquery>
<cfloop query=data_query">
<li>
<div class="list_div clearfix">
<input type="text" value="#URLDecode(name)#">
</div>
</li>
</cfloop>
</cfquery>

You have two options:
Wrap the vars output line with <cfoutput /> tags:
<cfoutput>#id#: <input type="text" value="#name#"></cfoutput>
Use <cfoutput query="data_query"> loop instead of <cfloop ...>
For the sake of cleaner code I would prefer the second option so your code would be:
<cfquery name="data_query" datasource="#dsn#">
SELECT
id,
name
FROM learning
</cfquery>
<cfoutput query="data_query">
<li>
<div class="list_div clearfix">
#id#: <input type="text" value="#name#">
</div>
</li>
</cfoutput>

Also you should properly 'scope' your query columns when outputting. This will make your code easier to maintain in future, e.g. you'll always know that #data_query.name# belonged to the query and wasn't some string set by some other piece of code somewhere. And it'll speed up page performance - if you don't scope variables (this applies to all types of variables, not just queries), then CF will loop through the different scopes until it finds something with this value. So by scoping, you prevent CF having to loop.
<cfquery name="data_query" datasource="#variables.dsn#">
SELECT
id,
name
FROM learning
</cfquery>
<cfoutput query="data_query">
<li>
<div class="list_div clearfix">
#data_query.id#: <input type="text" value="#data_query.name#">
</div>
</li>
</cfoutput>

On the whole your logic was fine.. just a few typos and minor changes needed..
Give this a try.
<cfquery name="data_query" datasource="#dsn#">
SELECT
id,
name
FROM learning
</cfquery>
<cfloop query="data_query">
<li>
<div class="list_div clearfix">
#id#: <input type="text" value="#name#">
</div>
</li>
</cfloop>

And if you didn't know about it:
<cfdump var="#data_query#">
OR
<cfdump var="#data_query#" abort>
Will give you a beautiful display of came back from your query, or in any variable or structure.

Related

Coldfusion: update table based on form selection

I have a form which allows users to assign multiple records to a technician by Area number. It does this by outputting a line for each area in the outstanding records with a select list of the joined technician:
<cfoutput query="getAreaList">
<div class="row">
<div class="col-xs-4">
<div class="form-group">
<label for="hub">DWS Area:</label>
<input type="text" name="oparea" id="oparea" value="#OpArea#" class="form-control" />
</div>
</div>
<div class="col-xs-4">
<div class="form-group">
<label for="sub">Assign to:</label>
<select id="series" name="sub" class="form-control">
<cfloop query="getTechAreas">
<cfif OpArea EQ getAreaList.OpArea>
<option value="#username#" class="#OpArea#">#Displayname#</option>
</cfif>
</cfloop>
</select>
</div>
</div>
</div>
</cfoutput>
The resultant output looks like this - two lists of data:
form.opArea: Area 4,Area 5
form.sub: PERSON1,PERSON2
My aim is to update my jobs table, where each row for the specific form.OpArea is updated with the name of the technician, form.sub.
How do I loop through each list and insert the correct tech name where the opArea is matched?
I have tried looping through the insert but the whole of the list is being inserted, not the currently evaluated list item. I'm currently just trying to insert this into a holding table to test my code:
<cfoutput>
<cfloop list="#form.oparea#" index="i">
<cfquery datasource="cfLKDM" name="insertdata">
insert into [DWS_General_Dev].[LogSure].[Holding]
(AreaNo)
values
('#form.oparea#')
</cfquery>
Thank you
You are getting the whole list because you are still referencing the form field form.oparea within your loop. Which contains the entire list. When looping over a list, as you are doing, the cfloop will populate the index variable with the current value of the list item during each iteration.
So instead of using form.oparea you should be using i in your example. You should change the name of that index variable to be more descriptive.
Like this for your example:
<cfloop list="#form.oparea#" index="i">
<cfquery datasource="cfLKDM" name="insertdata">
insert into [DWS_General_Dev].[LogSure].[Holding]
(AreaNo)
values
('#i#')
</cfquery>
Better yet change the index variable name to be more descriptive:
<cfloop list="#form.oparea#" index="thisOPArea">
<cfquery datasource="cfLKDM" name="insertdata">
insert into [DWS_General_Dev].[LogSure].[Holding]
(AreaNo)
values
('#thisOPArea#')
</cfquery>

Creating a structure as a button in ColdFusion

First off, I'm not really sure how to title this question so I apologize if it's vague. I am trying to create a shopping list using ColdFusion and I've ran into a bit of a snag. I want a delete button to appear next to the item that's been created. I have almost everything working, but I don't understand structures enough in ColdFusion to understand what I am doing wrong. Is it similar to a component in React.js? I ran into an issue saying that the variable "button" is not defined. I'm assuming this is because structkeyExists can't identify a single button. Why would this work for form and not for a button?
Here is my code:
<cfif structKeyExists(form, "submitButt")>
<cfquery datasource="ESC-ADD-TECH">
INSERT INTO Main(itemDesc) VALUES('#itemDesc#')
</cfquery>
</cfif>
<cfif structKeyExists(button, "delete_butt")>
<cfquery datasource="ESC-ADD-TECH">
INSERT INTO Main(itemDesc) VALUES('#itemDesc#')
</cfquery>
</cfif>
<cfquery datasource="ESC-ADD-TECH" name="items">
DELETE FROM Main
WHERE itemDesc = '#itemDesc#'
</cfquery>
<body>
<div id="myDIV" class="header">
<h2>My Shopping List</h2>
<form method="POST">
<input type="text" name="itemDesc" placeholder="Title...">
<input name="submitButt" type="submit" class="addBtn">
</form>
</div>
<cfoutput query="items">
<li>#items.itemDesc# <button class="delete" name="delete_butt">x</button></li>
</cfoutput>
</body>
Is there a way to do what I am trying to do here using a structure? Am I better off creating the button in javascript and try to create a structure as a boolean statement and just have javascript rewrite that value? Kinda just shooting in the dark here, but I would appreciate any and all help.
Thank you everyone!
So there isn't going to be a "button" structure from your form being submitted.
The first thing to remember is that a ColdFusion structure is just a collection of key/value pairs (similar to a JavaScript object), and unless the value is set, will be undefined.
In your case, the "form" struct exists because you are submitting your page back to itself with your input[type="submit"]. Which for a ColdFusion page, will create a form struct with keys for each named input within the submitted form, the values of which are pulled from those elements' value attributes.
If you are trying to use the form struct to handle deleting items, you may be better served using radio buttons/checkboxes to select which item(s) to delete, and set the action to take using the value attribute of your submit buttons.
Using your code as an example:
<cfparam name="form.action" type="string" default="none">
<cfswitch expression="#form.action#">
<cfcase value="insert">
<!---Your insert query goes here--->
</cfcase>
<cfcase value="delete">
<!---Your delete query goes here--->
</cfcase>
<cfdefaultcase></cfdefaultcase>
</cfswitch>
<!---Your select query--->
<body>
<form method="post" action="#">
<div id="myDIV" class="header">
<h2>My Shopping List</h2>
<input type="text" name="itemDesc" placeholder="Title...">
<button type="submit" name="action" value="insert">Submit</button>
</div>
<ul>
<cfoutput query="items">
<li>#items.itemDesc#
<input type="radio" name="delDesc" value="#items.itemDesc#"/>
</li>
</cfoutput>
</ul>
<button type="submit" name="action" value="delete">Delete</button>
</form>
</body>
In this case you will use form.itemDesc when inserting values, and form.delDesc when deleting items.

ColdFusion not able to read option value of a cfselect

I'm a beginner with ColdFusion and I'm just trying out some basic functions.. I tried to loop over a simple query and put the values in a of a element. As value for the element I tried to set the id of each record of the query. After submiting I tried to read the selected value but I only get
You have chosen #getAll.id#
Here is my Code:
index.cfm
<cfquery datasource="testdb" name="getAll">
select *
from Personen
</cfquery>
<cfform action="chosen.cfm" method="post">
<cfselect name="listPersons">
<cfloop query="getAll">
<option value="#getAll.id#"><cfoutput>#getAll.id# #getAll.name# #getAll.vorname# #getAll.gebdate# <BR></cfoutput>
</cfloop>
</cfselect>
<cfinput type="Submit" name="Senden" value="Senden">
</cfform>
chosen.cfm
<cfoutput>You have chosen #listPersons#</cfoutput>
Can you tell me where I've made the mistake?
You didn't put your value attribute in a cfoutput tag, so it's being processed as #getAll.id# as the key in the struct instead of the value from the query. If you update your cfloop to be a cfoutput your issue will be fixed.
A couple pointers - You should scope the variable on chosen.cfm and you don't need to use cfform a regular form works just fine.
<cfquery datasource="testdb" name="getAll">
select *
from Personen
</cfquery>
<form action="chosen.cfm" method="post">
<select name="listPersons">
<cfoutput query="getAll">
<option value="#getAll.id#">#getAll.id# #getAll.name# #getAll.vorname# #getAll.gebdate#</option>
</cfoutput>
</select>
<input type="Submit" name="Senden" value="Senden">
</form>
chosen.cfm
<cfoutput>You have chosen #form.listPersons#</cfoutput>
Your code works for me with my test database but the value of listPersons on Chosen.cfm is not what I think you intended it to be. I would change the code to the following:
<cfquery datasource="testdb" name="getAll">
select *
from Personen
</cfquery>
<cfform action="chosen.cfm" method="post">
<cfselect name="listPersons">
<cfoutput query="getAll">
<option value="#getAll.id#">#getAll.id# #HTMLEditFormat(getAll.name)# #HTMLEditFormat(getAll.vorname)# #getAll.gebdate#
</cfoutput>
</cfselect>
<cfinput type="Submit" name="Senden" value="Senden">
</cfform>
What I did is I changed your CFLOOP to a CFOUTPUT then removed the CFOUTPUT you had. I also added the HTMLEditFormat functions just in case NAME or VORNAME contain some characters that will not play nice with the display. I assumed ID is numeric and GEBDATE is a date so figured no need on those. I also removed the BR element from your OPTION, not that I thought it was causing an issue but I could not see how that would effect the display either so seemed unneeded. I'd personally would close the OPTION but it is not needed to run. If you ultimate code is not running anything that CFFORM offers then I'd not use it and just use an HTML FORM.
Then on Chosen.cfm I would scope the output:
<cfoutput>#Form.listPersons#</cfoutput>
<cfoutput query="getAll">
#id# #name#
</cfoutput>
You don't need to repeat the query name inside of a cfoutput loop, if with cfoutput you specify the query you are looping over.

displaying questions twice

can anyone review this code tell me what's wrong in it? I don't understand why it is displaying questions two times.
here is the code to display questions based on its questiontype, I mean it will look into question folder for matching questiontype template and then display it with question.
this is the code to show survey's questions.
<cfoutput>
<cfset step = 0 />
<form class="form form-horizontal" action="#buildUrl(action='survey.savesurveyresults',querystring='surveyId=#rc.surveyid#')#" method="post">
<input type="hidden" name="id" value="0">
<input type="hidden" name="fksurveyid" value="#rc.surveyId#">
<input type="hidden" name="fkquestionid" value="#rc.questions.id#">
<fieldset>
<cfloop query="rc.questions">
<cfset step ++ />
<cfset answer = "" />
<cfmodule template="../question/#rc.questions.template#/display.cfm" step="#step#" question="#rc.questions.question#" template1="#rc.questions.template#" fkquestionid="#rc.questions.id#" answer="#answer#" required="#rc.questions.required#" result="result#step#"/>
</cfloop>
<div class="form-actions">
<button type="submit" name="submit" class="btn btn-success">Submit answers</button>
</div>
</fieldset>
</form>
</cfoutput>
this is my display.cfm to view question and its questiontype like truefalse or yes or no.
<cfparam name="attributes.yesno" default="false">
<cfoutput>
<p>#attributes.step#) #attributes.question# <cfif attributes.required EQ 1><strong>* </strong></cfif></p>
<div class="answers">
<cfif attributes.yesno>
<input type="radio" name="answer" id="answer" value="yes"<cfif attributes.answer is "yes">Checked</cfif>><label for="truefalse">Yes</label><br>
<input type="radio" name="answer" id="answer" value="no"<cfif attributes.answer is "No">Checked</cfif>><label for="truefalse">No</label>
<cfelse>
<input type="radio" name="answer" id="answer" value="true"<cfif attributes.answer is "true">Checked</cfif>><label for="truefalse">True</label><br>
<input type="radio" name="answer" id="answer" value="False"<cfif attributes.answer is "False">Checked</cfif>><label for="truefalse">False</label>
</cfif>
</div>
</cfoutput>
here is the query to list question's records.
<cfquery name="list">
SELECT
questions.id,
questions.question,
questions.rank,
questions.required,
questiontypes.name as questiontype,
questiontypes.template as template,
surveys.name as surveysname,
surveys.thankyoumsg as thankyoumsg
FROM questions
INNER JOIN questiontypes ON questions.fkquestiontypeid = questiontypes.id
INNER JOIN surveys ON questions.fksurveyid = surveys.id
WHERE questions.fksurveyid = <cfqueryparam cfsqltype="cf_sql_bigint" value="#arguments.surveyid#">
</cfquery>
This is something that has bitten me a couple of times. I've always been pretty big on closing tags. But this is a situation where it will hurt. And be hard to debug if you don't understand the behavior of cfmodule. As the post above mine states, if you close the cfmodule tag, it will execute twice. This is because it's treated the same as a custom tag. There may be situations where you want to process part of the tag when it's first run and the rest after it's complete. You can access the ExecutionMode in the thisTag scope of the cfmodule page. With no closing tag, it's simply run in the thisTag.ExecutionMode = Start mode. If you close it, it runs the tag again in the End mode. If you aren't doing anything with the ExecutionMode inside the cfmodule's code, the whole thing will simply run again. This behavior is part of the reason that cfmodule can be so powerful.
When using the <cfmodule> tag you need to remember that ColdFusion will call that tag twice if you include an ending </cfmodule> tag OR if you close the opening tag like so <cfmodule ... />.
As stated on the cfmodule documentation page:
If you specify an end tag to cfmodule, ColdFusion calls your custom tag as if it had both a start and an end tag. For more information, see Handling end tags in the Developing ColdFusion Applications.
Handling end tags in the Developing ColdFusion Applications
In order to avoid this functionality do not close your <cfmodule> tag.
I got it, i must have not to close the cfmodule tag like <cfmodule />.

ColdFusion query dropdownlist

Is it possible to populate a dropdown list with query results? For example with this output: Peps Company - AL ie (Company and State) separated with a hyphen.
Edit: Sorry for leaving out code. There is only one datasource.
<cfquery name="CompanyInfo" datasource=>
SELECT company, state
FROM clients
WHERE serv_billing = 1
AND status = 'Active'
ORDER BY Company
</cfquery>
<FORM METHOD="POST" ACTION="nextpage.cfm">
<SELECT name="company">
<CFOUTPUT QUERY="CompanyInfo">
<OPTION value="#CompanyInfo.company#">#CompanyInfo.company# - #CompanyInfo.state#</OPTION>
</CFOUTPUT>
</SELECT>
<INPUT TYPE="submit" VALUE="Submit Company">
</FORM>
Would this code give me the desired format for the dropdown list items ie Peps - AL?
?
The answer is yes. This code will do precisely that.
Does it not work? Do you have a problem with it, or..? I find it strange that you didn't simply try it out because you already seem to have the code to do what you want to do.
Seybsen's answer is technically correct, however, I would compel you to follow best practices and perform a single loop, rather than iterative returns to the database on each row result of the main query:
<CFQUERY name="qCompanies" datasource="yourdsn">
SELECT companies.id, companies.company, states.state_code
FROM companies
INNER JOIN states ON (companies.state_id = states.state_id)
</CFQUERY>
<SELECT name="company">
<CFOUTPUT QUERY="qCompanies">
<OPTION value="#qCompanies.id#">#qCompanies.company# - #qCompanies.state_code#</OPTION>
</CFOUTPUT>
</SELECT>
You can do it with cfloop like this:
<cfquery name="CompanyInfo" datasource="yourdsn">
SELECT company, state
FROM clients
WHERE serv_billing = 1 AND status = 'Active'
Order by Company
</cfquery>
<FORM METHOD="POST" ACTION="nextpage.cfm">
<SELECT name="company">
<CFLOOP QUERY="CompanyInfo">
<OPTION value="#CompanyInfo.company#">#CompanyInfo.company# - #CompanyInfo.state#</OPTION>
</CFLOOP>
</SELECT>
<INPUT TYPE="submit" VALUE="Submit Company">
</FORM>