#1 2015-02-22 05:17:59

tomharney
Member
Registered: 2014-03-11

URL variables - Groovy Scripts

I posted this question last fall.  http://forum.reportserver.net/viewtopic.php?id=199

How does one retrieve the url variables in a Groovy script?

ReportServer.html?locale=en&username=abelincoln

Would you use this library?  For example, how would I retrieve the value username or locale?

http://www.gwtproject.org/javadoc/lates … t/URL.html

I'm still having trouble understanding how everything fits together.

As always, thank you for your guidance!

Offline

#2 2015-02-22 08:52:51

Arno Mittelbach
datenwerke
Registered: 2012-02-14

Re: URL variables - Groovy Scripts

Hi Tom,

you can access the servlet request object (if available) via:

def requestProvider = GLOBALS.getProvider(HttpServletRequest.class)
HttpServletRequest req = requestProvider.get()

Instead of getProvider() you might need to use getRsServiceProvider() depending on your version.
You can also use GLOBALS.getInstance() (or getRsService() in older versions) to directly retrieve an instance instead of a provider.

The ServletRequest then allows you to access the URL parameters, for example, via

req.getParameter("user")

See http://docs.oracle.com/javaee/6/api/jav … quest.html for some additional information.

Putting it all together:

import javax.servlet.http.HttpServletRequest

def requestProvider = GLOBALS.getProvider(HttpServletRequest.class)
HttpServletRequest req = requestProvider.get()

return "User: " + req.getParameter('user')

Finally, if you are planning to execute the script via the scriptAccess Servlet, then you can access the request directly via the then predefined variable
httpRequest. Thus, the above could be shortened to

return "User: " + httpRequest.getParameter('user')

Cheers
Arno

Offline

#3 2015-02-22 14:47:20

tomharney
Member
Registered: 2014-03-11

Re: URL variables - Groovy Scripts

Fantastic!  I'm quite familiar with servlets.  Thanks, Arno!

Offline

#4 2015-02-22 19:00:41

tomharney
Member
Registered: 2014-03-11

Re: URL variables - Groovy Scripts

This seems like such an elementary question but unfortunately, I'm not able to access the GLOBALS object using the ShiroPAM example.

It seems like maybe I should be hacking the IPRestrictionPAM module instead.

It provides example of how to access the HttpServletRequest.

For example: Provider<HttpServletRequest> requestProvider

My plan and I do plan to use the scriptAccess servlet.

1)  Call a script passing the username from a third-party web app. (password authenticated of course)
2)  If the user is found in ReportServer, it will return a randomly generated number or a GUID, storing it in a table in the Report Server db
3)  The third-party web app will redirect to ReportServer.html?guid=[insert guid or number]
4)  The authenticator hook will verify the GUID exists and login the user

It is important that I am able to read url parameters in the authenticator module.

Thoughts?

Offline

#5 2015-02-22 21:02:49

tomharney
Member
Registered: 2014-03-11

Re: URL variables - Groovy Scripts

So far I have this... The HttpServletRequest appears to be null (according to the output of the logger).  I'm not quite sure how (or if it's even possible) to pass GLOBALS to the ShiroPAM class.

package pam

import net.datenwerke.rs.authenticator.client.login.dto.UserPasswordAuthToken
import net.datenwerke.rs.authenticator.client.login.pam.UserPasswordClientPAM
import net.datenwerke.security.client.login.AuthToken
import net.datenwerke.security.service.authenticator.AuthenticationResult
import net.datenwerke.security.service.authenticator.ReportServerPAM
import net.datenwerke.security.service.authenticator.hooks.PAMHook
import net.datenwerke.security.service.usermanager.UserManagerService
import net.datenwerke.security.service.usermanager.entities.User

import javax.servlet.http.HttpServletRequest

import net.datenwerke.rs.scripting.service.scripting.scriptservices.GlobalsWrapper

import com.google.inject.Inject;
import com.google.inject.Provider;

import java.util.logging.Logger;
 
Logger logger = Logger.getLogger("ShiroPAM");
logger.severe("@@@@ ShiroPAM INIT @@@@");

requestProvider = GLOBALS.getProvider(HttpServletRequest.class);
HttpServletRequest req = requestProvider.get();

final ShiroPAM shiroPAM = GLOBALS.injector.getInstance(ShiroPAM.class);
GLOBALS.services.callbackRegistry.attachHook("SHIRO_PAM", PAMHook.class, new PAMHook(){
	
	public void beforeStaticPamConfig(LinkedHashSet<ReportServerPAM> pams){
		pams.add(shiroPAM);
	}
	public void afterStaticPamConfig(LinkedHashSet<ReportServerPAM> pams){
		
	}
	
});


public class ShiroPAM implements ReportServerPAM {
	
	private final UserManagerService userManagerService;
    private final Provider<HttpServletRequest> requestProvider;
    private final GlobalsWrapper GLOBALS;
  
	Logger logger = Logger.getLogger("ShiroPAM");  
  
	@Inject
	public ShiroPAM(Provider<HttpServletRequest> requestProvider,
                    UserManagerService userManagerService) {
		this.userManagerService = userManagerService;
        this.requestProvider = requestProvider;
	}
	
	@Override
	public AuthenticationResult authenticate(AuthToken[] tokens) {

        // So if you have an SSO solution, this authenticate method will be your point of extension. 

		//def requestProvider = GLOBALS.getProvider(HttpServletRequest.class);
		HttpServletRequest req = requestProvider.get();
        
        String username = "";
        String paramname = "uid";
        logger.severe("Query string:" + req.getQueryString());
        logger.severe("Parameter: " + req.getParts());
		username = req.getParameter(paramname);
        //username = "root";
      
    	return new AuthenticationResult(true, userManagerService.getUserByName(username),true);
		
	}

	@Override
	public String getClientModuleName() {
		return null;
	}
}

Offline

#6 2015-02-23 02:44:17

tomharney
Member
Registered: 2014-03-11

Re: URL variables - Groovy Scripts

I've also implemented my own custom Java class to no avail.

I was able to successfully register it in the report.properties file but the HttpServletRequest contains no data from the ReportServer.html url.

http://[server]:8080/reportserver/ReportServer.html?locale=en&uid=abelincoln

I'm trying to read abelincoln from the url querystring.   Should I be taking a different approach?  Will this HTML page even pass the entire querystring to reportserver?

See below:

package net.datenwerke.rs.authenticator.service.pam.custom;


import java.util.logging.Logger;

import javax.servlet.http.HttpServletRequest;

import net.datenwerke.rs.utils.misc.IPUtils;
import net.datenwerke.rs.utils.properties.ApplicationPropertiesService;
import net.datenwerke.security.client.login.AuthToken;
import net.datenwerke.security.service.authenticator.AuthenticationResult;
import net.datenwerke.security.service.authenticator.ReportServerPAM;
import net.datenwerke.security.service.usermanager.UserManagerService;
import net.datenwerke.rs.utils.crypto.PasswordHasher;

import com.google.inject.Inject;
import com.google.inject.Provider;

/**
 *
 * @author Tom
 */
public class CustomAuthenticatorPAM  implements ReportServerPAM{

	private final Logger logger = Logger.getLogger(getClass().getName());

	private final static String IP_ADDRESSES_PROPERTY_NAME = "rs.authenticator.iprestriction.addresses";

	private final Provider<HttpServletRequest> requestProvider;
	private final ApplicationPropertiesService propertiesService;
	private final IPUtils iputils;
        private final UserManagerService userManagerService;
        private final PasswordHasher passwordHasher;
	
	@Inject
	public CustomAuthenticatorPAM(
			Provider<HttpServletRequest> requestProvider,
                        UserManagerService userManagerService,
			ApplicationPropertiesService propertiesService,
                        PasswordHasher passwordHasher,
			IPUtils iputils) {
		this.requestProvider = requestProvider;
		this.propertiesService = propertiesService;
		this.iputils = iputils;
                this.userManagerService = userManagerService;
                this.passwordHasher = passwordHasher;
	}

	public AuthenticationResult authenticate(AuthToken[] tokens) {
		/* load ip addresses */
		String ipAddresses = propertiesService.getString(IP_ADDRESSES_PROPERTY_NAME);

		/* get request */
		HttpServletRequest request = requestProvider.get();
		String remoteAddress = request.getRemoteAddr();
                String uid = request.getParameter("uid");
                /*
		for(String ipString : ipAddresses.split(":")){
			ipString = ipString.trim();

			if(iputils.contains(ipString, remoteAddress))
				return new AuthenticationResult(true, null);
		}
                */
                logger.info("UserID: " + uid);
                logger.info("Remote Address: " + remoteAddress);
		//logger.info("Blocked access from: " + remoteAddress);
                return new AuthenticationResult(true, userManagerService.getUserByName(uid),true);
		//return new AuthenticationResult(true, null);
	}


	public String getClientModuleName() {
		return null;
	}


}

Offline

#7 2015-02-23 12:02:54

Thorsten J. Krause
datenwerke
Registered: 2012-02-15
Website

Re: URL variables - Groovy Scripts

Hi Tom,

the url parameters used with the ReportServer.html page are not available in authenticator modules, but the authentication scheme you describe should work without it:

In addition to the script you use to generate your uids create a second script, that validates the uids, logs in the user and issues a redirect to the host page.

import net.datenwerke.security.service.authenticator.AuthenticatorService
 
def service = GLOBALS.getRsServiceProvider(AuthenticatorService.class).get()
def guid = httpRequest.getParameter("uid")

if(isValid(guid)){
  service.setAuthenticated(getUserIdForGuid(guid))
  httpResponse.sendRedirect("http://example.com/ReportServer.html");
  return null 
} 

And have the external application redirect the users to this script instead of the reportserver main page.

Cheers,
Thorsten

Offline

Board footer

Powered by FluxBB