Prior to Confluence 4.3, it was easy to add template variables anywhere in the template. Is this capability gone in Confluence 4.3?
Also, when editing a template and using Insert Wiki Markup, I keep getting "Wiki Markup Conversion Errors - error:Bad Request" when the inserted wiki contains a macro (like {info} for example). Same problem on Confluence 5.0.
I have done some tinkering on this subject and have come up with a (less than perfect) user macro that will work in a lot of cases. "Less than perfect"? Well it seems the user macro rendring of $body ruins the layout of sections on the page if JIRA macros are included. In practise this makes side-by-side JIRA issue tables impossible, outside of that I have tried sections and columns with success.
Macro name: applytemplatevars Macro Title: Apply Template Variables Description: This macro encases other macros so that template variables can be transferred to them. Categories: Confluence Content Macro Body Processing: Rendered Template: ## Macro title: applytemplatevars ## Macro has a body: Y ## Body processing: Rendered ## Output: body with replaced variables ## ## Developed by: Kim Poulsen ## Date created: 28/09/2015 ## Installed by: <you?> ## @noparams ## Fish out the parameter section of the body: ###################################### #set ($lbody = $body) #set ($idx = $lbody.indexOf("</p")) #set ($params = $lbody.substring(3, $idx)) ## Replace the body with the real body (without the variable section) #set ($body = $lbody.substring($idx)) ## This version accepts <name>=<value>|<name>=<value>|... type specification ################################################################# #foreach($v in $params.split("[|]")) ## Fish out variable names and values: ####### #set ($varArr = []) #foreach($i in $v.split("[=]")) #set ($retval = $varArr.add($i) ) #end #set ($vn = $varArr.get(0) ) #set ($vv = $varArr.get(1) ) ## And do the replacement: ######## #set ($body = $body.replaceAll($vn, $vv) ) #* ## Change the page title as well (dangerous: The page will change title, and possibly get lost.) #set ($title = $content.getTitle() ) #set ($title = $title.replaceAll($vn, $vv) ) $content.setTitle($title) *# #end $body
Use it like this:
I'd appreciate any input on how to not get output ruined when using JIRA macros in a rendered $body.
Edit: Obviously the macro can also be used without template variables. Just type in the string you want to substitute and all is good too.
To add to the case it seems Confluence does more to the body after the JIRA macro: <div class="hidden"> <textarea id="refresh-wiki-2035414160"> <input id="refresh-page-id-2035414160" type="text" value="7375841" /> </div> <p /> </div> <p /><h5 id="... ... </textarea> The "class=hidden" effectively eats everything below that point on the page. And the textarea converts it all to a string, so bye bye remaining page.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
@Kim Poulsen thank you for your comment. I got this working, but it replaces variables in the body-output only. It does not replace variables, I pass to the makro as parameter (as the title of this thread is suggesting). Is that correct?
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
@Dougi B The macro should replace all variables in text and macros put into the body of the "applytemplatevars" macro. I cannot post images here, but lets try this in text:
/applytemplatevars/
/ VAR1=Hello|VAR2=World
/ VAR1 VAR2
/-------------------------
This would print on screen:
Hello World
Another one:
/applytemplatevars/
/ VAR1=Hello|VAR2=World
/
/Panel(title=VAR1) /
/ VAR2 /
/------ /
Other text from the big VAR2 /
/----------------------------/
This would print on screen:
/-----------------------------/
/ Hello /
/----------- /
/ World /
/----------- /
Other text from the big World /
/-----------------------------/
So in the case I set the Title of the panel to the value "VAR1" and the body of the panel to "VAR2" I also re-use VAR2. You can use this together with template variables "$myVar" if you like. It looks like the mechanism is as simple as Confluence substituting $myVar when generating the draft page. So using them as variable values in this macro, you get to input data from the template generation stage too. It get's complicated without images, so I hope you understand the crude drawings above. The only case where I cannot get this to work is when using JIRA macros - which was actually where I started looking into this :-)
Edit: Fix formatting.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
I think the title in your example was replaced in the output of the macro. In my case I pass an URL to an macro, which downloads and inspect a file. Unfortunately I don't have access to the logsfiles, but I verified this by adding the value "MyValue" of the parameter ("MyParametername") to the output. It gets replaced. but when I split the value I get "My" "Parametername" in the output. The parameter has never been replaced.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
@Dougi B: Okay so you have something like: URL=http://my-fileserver.sth/filespec.txt And a Macro, where you specify an URL field with "URL" in it? I must admit that I haven't tried to use it in such a clever way :-) I've tested it out now though, and while replacement does happen as expected (i.e. URL gets substituted) it uses whatever formatting Confluence choses for links. This means wrapping stuff in <span> tags etc. I can get to the point where I need to whitelist a site by putting in the HTML include macro "http:/mysite.com/MYVAR" and define MYVAR=my/path/to/the/page.html Confluence does not do any further automatic formatting on a string like that and actually attempts to retrieve a page from mysite. Then again, this macro is not a generic solution, it manipulates the page content before rendering, and any pre-processing Confluence might think is a good idea could interfere with any good intentions here :-)
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Pretty nifty macro. One problem I'm having. It seems to work for macros like "panel" and "info" but not for macros like "recently-updated" or "contentbylabel". The variable text doesn't get replaced in those. Any thoughts as to why?
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Sorry, I have no idea. The macro is pretty brute force in nature as it simply replaces all matching stings with the substitution string, so perhaps these macros hide their parameters in a format this macro doesn't get around to do substitutions in. If you take a look at the storage format of the page with those macros you might get a hint of this. I envision that label names are encapsulated in some extra tags for instance.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
This is such a tantalizing macro, but I can't figure out how to use it. (I'm new to user macros). I created a new User Macro, cut&paste your code into the Template field, and saved it. Then in a sandbox, I typed \{applytemplatevars} (without the forward slash). But when I previewed the page, all I saw was "Error rendering macro 'applytemplatevars' : Error occurred rendering template content". Can you please provide a step by step example of exactly how to use this code? THank you!
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Hey @Kim Poulsen,
thanks for your user macro. Unfortunately I have a strange bug which makes it unusable to me:
The macro works in the macro preview and in the page preview, correctly replacing the variables. But once the page is saved, the substitution does not work anymore and the variable name is displayed again.
Do you have any clue what could cause such behaviour?
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Hi @Kevin Mote.
One case where the macro will throw "Error rendering" is if you are not specifying any variables in the first line of the macro body. I assume you have checked the "Rendered" button in the User Macro editor.
So when looking at the storage format, it should look like this:
<ac:structured-macro ac:macro-id="aca752e4-35f4-4534-a87d-d4d164e0ed35" ac:name="applytemplatevars" ac:schema-version="1">
<ac:parameter ac:name="atlassian-macro-output-type">INLINE</ac:parameter>
<ac:rich-text-body> <p>VAR1=Test</p> <p>Here's: VAR1</p>
</ac:rich-text-body>
</ac:structured-macro>
Here I have just defined one variable "VAR1=Test", and use it in the sentence below: "Here's VAR1".
Want more variables? Just specify them in this format:
VAR1=Tara|VAR2=Tarb|<and so on>
They just have to be in the first line, that's all.
I hope this helps you and possibly others.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Hi @Alexander Schöcke.
The macro is quite brute force in nature, so maybe the places where you try to substitute, are not exposed in such a way that e.g. a variable VAR1 is like this in the storage format.
If you look at the page storage format, you should be able to see what's going on. I know that drop-downs, people selectors and stuff like that is not usable with this macro for the above reason.
I have a hard time saying more, as I don't know on what you try to apply the substitution, but I hope this helps a little.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Hey @Kim Poulsen,
thank you for your answer. I basically tried this on an empty page in order to rule out any incompatibilities with other macros or the like, so the storage format ist not more than this:
<ac:macro ac:name="applytemplatevars">
<ac:parameter ac:name="atlassian-macro-output-type">BLOCK</ac:parameter>
<ac:rich-text-body>
<p>VAR1=WARRRRR</p> <p>Display VAR1</p>
</ac:rich-text-body>
</ac:macro>
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Hi @Alexander Schöcke,
We're running Confluence 5.8.9 btw.
You storage format looks almost like my example above. I wonder if the "BLOCK" vs. "INLINE" makes the difference? I cannot get the macro here to use "BLOCK", so I wonder where that might come from.
The other difference is that your storage format is not a "structured-macro", but just a "macro", so something is wrong here. Also here I cannot reproduce that output.
I'm sorry, I don't think I have the insight to aid on this one.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
This doesn't appear to work if the macro you insert into the body is a user macro. I suspect it is due to the order user macros are rendered in, or because there is only one render "pass", both of which are outside of our control.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Hi @Kim Poulsen,
I have tried using your code in a user macro but I get rendering error, so I assumed I am doing something very basic wrong.
What I am going to achieve is to create a page template, define a $projecKey variable in the beginning of it and some macros following that. When the user creates a page from the template, they are asked to insert project key and the key should be delivered to like 10 other macros, which those will use the key in a jQuery for fetching data from some REST API. I only need and have one variable for all of those macros and that only one is the project key which I defined in the first line of template.
That said, I do as follows:
1- Create a user macro, set it to rendered and paste your code inside it (untouched)
2- I a page template, insert a variable from top menu and call it projectKey. So it makes it green and shows as $projectKey
3- Following that, I insert the macro I created in step number 1.
Question here is, at this stage what should be written inside this macro, I just inserted in?
"mySuperTemplatevar=$projectKey|", this leaves me with rendering error.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Here's a very basic example (now in color):
when generating the page:
And rendered:
From what you write I suspect you write "$projectKey", not the "green $projectKey".
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Tack for the magic, @Kim Poulsen :) it worked!
The only thing was that $body returned the variable's value with some extra tags like: <p></p>thevalue</p>. Had to run (/<(.|\n)*?>/g, '') on it.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Just ran into this issue as well. CONF-3324 has been open a surprisingly long time with no real "desire" from Atlassian to fix it. I'm a little baffled honestly with how good their product seems to be. Not sure how this issue could be viewed by them as a "nice to have" for their Blueprints feature. To me it is just straight broken if this doesn't work, they lose all their power to be used for anything beyond a very simple formatted text page. Very disappointed right now. :(
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Any updates about this? I'm currently evaluating Confluence and I need some functionality like this one... +1
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
You can watch this issue, but I wouldn't hold your breath https://jira.atlassian.com/browse/CONF-3324
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Hallo Bob and Eddie
I'm not exactly sure what you're asking ;) but could it be the same as this discussion in our doc space?
Cheers, Sarah
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Must have missed this earlier. It covers part of it. The part about variables in plain text bodies is not covered.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Is there a bug or improvement open for this issue? Is there any way to work around this problem?
I use this feature in many of my Confluence 4 templates for many reasons. Here's one example:
Enter label of projects: @PROJECT_LABEL@ {checklist:name=Project Information|parent=Home|usecanvas=false|label=@PROJECT_LABEL@|depth=4} {checklist-input:cols=20|heading=Tech Lead|rows=1} {checklist-input:cols=40|heading=JIRA Versions|rows=1} {checklist-input:cols=20|heading=Bamboo Key|rows=1} {checklist}
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
I was able to pass a template variable to a macro in the following way:
## Macro title: My Macro ## ## Developed by: My Name ## Date created: dd/mm/yyyy ## Installed by: My Name ## @noparams <ac:macro ac:name="contentbylabel"> <ac:parameter ac:name="label">$body</ac:parameter> <ac:parameter ac:name="operator">AND</ac:parameter> </ac:macro>
Simple but it works.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
This is a simple solution, and that is an advantage. The disadvantage is that it is also tailored for a single purpose because you have to insert any and all macros you want in here, or create one user macro for each type of default macro you want to use template variables with. Another disadvantage is that you can only use a single variable in this case. My solution works for any number of variables and can substitute any number of contained macros and any number of fields in those macros. The disadvantage is that JIRA macros seem to render themselves in a way that puts the remainder of the page into a hidden <textfield>. This is where your solution comes in handy because the use is them limited to e.g. the JIRA macros. Thanks for sharing.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
I tried this solution in confluence 5.4.2 but it doesn't work for me. Is this working in JIRA only? I pass 4 variables as macro parameter to the macro, two of them are urls. the macro only gets $variablename. I tried both, insert to the body of the wrapper-macro: $variablename or $$variablename.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
@Dougi B: The macro Kate describes only works because the $body variable contains the body of the macro, and the body of the macro becomes the label text in this case. In other words, you will not have any other variable names available to you in this example. My own solution further above splits the $body into separate variables, which are then substituted into other macros instantiated inside the body of the wrapper macro.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
I think the closest you'll get to this functionality is through writing your own User Macros:
https://confluence.atlassian.com/display/DOC/Adding%2C+Editing+and+Removing+User+Macros
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Any updates about this? I'm currently evaluating Confluence and I need some functionality like this one...
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
We also have got a similar issue.
We want to create a page template using one variable (issue key) that will be used by the SQL macro.
This mechanism will allow the users to have a page already pre formated with a set of macros (here this is SQL macros) using the value of an issue required during the page creation.
The template will look like:
Type the value of the issue_key: $variable
{sql:dataSource=xxxx} select i.issue_key, i.issue_type, i.timespent from issue where i.issue_key = 'Eval of $variable' (here I would like to have the value of the variable selected) {sql} ...... ......
Does somebody help us ?
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Yes, I poked a couple of times.
BTW, I don't think the Variables insert thing is very obvious for people that knew the old way of doing things. I took me a while to notice that in the editor. So actually your post would be helpful for some other folks.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Yes, I poked a couple of times.
BTW, I don't think the Variables insert thing is very obvious for people that new the old way of doing things. I took me a while to notice that in the editor. So actually your post would be helpful for some other folks.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Sorry for my confusion before. Even the former work around of declaring the variable outside the scope of the macro parameters does not make them replaced within the parameter. Have you "poked" atlassian about this, or submitted a ticket? Seems some functionality has regressed.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Perhaps I am misunderstanding, but in Confluence 5 you can define variables anywhere, including inside macros like the info box.
The "insert wiki markup" (ctrl+shift+d) also seems to work for me.
Space tools > content tools > page templates
https://confluence.atlassian.com/display/DOC/Adding+a+Template
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.