I have a string like this that I get from a database:
[email protected]&name=John
I'd like to know if there is an easy way to extract the data and put them into two variables, user and name.
You create most ColdFusion variables by assigning them values. (You must use the ArrayNew function to create arrays.) Most commonly, you create variables by using the cfset tag. You can also use the cfparam tag, and assignment statements in CFScript.
Use an Array of Variables The simplest JavaScript method to create the dynamic variables is to create an array. In JavaScript, we can define the dynamic array without defining its length and use it as Map. We can map the value with the key using an array and also access the value using a key.
@Marc, As per @Dan Bracuk suggestion you can split your string by using mentioned delimeter first as &
and again as =
. Please refer my below code that will help you. I hope.
Runnable Example
<cfset yourInput= '[email protected]&name=John'>
<!--- Get the first value. I mean "user" part --->
<cfset splitFirstPart = listfirst(yourInput,'&', true)>
<cfset splitLastPart = listlast(yourInput, '&', true)>
<!--- Get the second part value --->
<!--- Above values are split by using & --->
<cfset user = listlast(splitFirstPart, '=', true)>
<Cfset name = listlast(splitLastPart, '=', true)>
<!---
Now we can again split the list by using =.
Now you can see the result.
--->
<cfoutput>
User : #user# <br/>
Name : #name#
</cfoutput>
If you need any other CFML functions & clarification please refer https://cfdocs.org/
Thanks.
Here is my take on how to solve this one.
I like having a structure as final result. I also like working with the each functions as an implicit loop.
<cfscript>
yourInput= '[email protected]&name=John';
variables.result = {};
ListEach(yourInput,
function(item) { variables.result[listfirst(item, "=")] = listLast(item, "="); },
"&");
writedump(result);
</cfscript>
To add to this answer for future readers, there are a couple of ways to make this more dynamic.
Essentially, you are just parsing a delimited list twice and pulling out the pieces you need. ColdFusion allows several ways to do that.
For illustration, I've added to the original string.
string="[email protected]&name=John&somethingelse=42&foo&base64Msg=QmVFeGNlbGxlbnRUb0VhY2hPdGhlcg==" ;
My preferred way to parse this is to us a CF function that returns a struct of all of the pieces I need.
public Struct function parseURLParamString( required String inURLStr ) {
/// Initialize the return struct.
var retStruct = {} ;
// Use listEach() function to iterate over the list with delim "&"
arguments.inURLStr.listeach(
function(item){
// listFirst gets 1st list element. listRest() gets all but 1st element. Delim "="
retStruct[listFirst(item,"=")] = listRest(item,"=") ;
}
, "&"
) ;
return retStruct ;
}
writeDump( parseURLParamString(string) ) ;
This will return:
Then you can just reference the variables you need from your returned struct.
But if you need to create actual variables instead of pulling them from a struct, you can do so like this:
arguments.inURLStr.listeach(
function(item){
variables[listFirst(item,'=')] = listRest(item,"=") ;
}
, "&"
) ;
... and then change your outer function to either return Void
or nothing and drop the struct from it. You can reference the variables like user = #user#
. This would require you to know the variables in advance, whereas when passing a specific struct, you can just loop over the struct and output the keys/values. Technically you can also loop over the variables
scope, but there will likely be a lot of other variables in there, too.
If you want, you can also use getToken()
, but it has the same limitation that listLast()
does. If your value
contains the second delimiter text (like a padded Base64 string), then those characters would be treated as a delimiter and be left off of your value. For base64Msg = QmVFeGNlbGxlbnRUb0VhY2hPdGhlcg==
, getToken()
/listLast()
will return QmVFeGNlbGxlbnRUb0VhY2hPdGhlcg
, where listRest()
will give you QmVFeGNlbGxlbnRUb0VhY2hPdGhlcg==
. Or even worse, if the character is in the middle of the string, it will be truncated. ListLast()
removes the first item of a delimited list and returns the rest of the list, so if your string contains the delimiter, it will return the full value.
Lastly, since this appears to be a string from a URL, you probably want to sanitize and encode the string before you store it in the database.
If you save the encoded value, it will likely turn your delimiters into their encoded values. The above frunctions only support single-character delimiters, so wouldn't be usable as above (unless decoding before sending to the splitting function). listToArray
allows multi-character delimiters. So that may be one way to split them.
In the end, there are a lot of characters that are allowed a URL string, #
and =
being two that are sure to cause you issues without encoding and proper handling.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With