CASyfing Open Upload
openupload-0.4.2-patch-casyfing.patch
Open Upload is a PHP application to create a private / public file download server similar to MegaUpload or RapidShare.
Version 0.4.2 offered only two types of authentication: default and ldap. With these types of authentication, you must use Open Upload's login form.
The goal is modify application to accept authentication from an external form-based.
mod_auth_cas, or PHPCAS, that is the question
In both cases, you must modify source code. But I prefer to use mod_auth_cas for three reasons :
- When user is authentified, user code can be written in the Apache access log.
- You can CASyfing many applications with the same module (if installed on Apache proxy).
- This patch can be reused for any form-based authentication.
Source code modifications
I found a patch on sourceforge website (see url below). This patch adds a new authentication type called httpldap. I modified this patch to add new features.
My new features are :
- Added a logout url.
- Display an error message when it can't get the list of LDAP groups to the user.
- Block access to the Open Upload's login form.
The following sections describe changes to the application.
New parameters
First changes are : adding a new type of authentication httpldap and two new parameters for this new type.
In config.inc.php file
auth parameter
You must specify the type httpldap.
login parameter (NEW)
The value is the name of the variable whose content is the user code.
- User code from mod_auth_cas (Directive CASAuthNHeader).
- Remember, if mod_auth_cas is installed on Apache proxy, the variable name is prefixed with HTTP_.
urlexit parameter (NEW)
The value is a URL where user will be redirected after logout.Â
show 1
You can see an example of setting in the config.inc.php.example file.
Â
Index: www/config.inc.php.example
===================================================================
@@ -44,6 +44,14 @@
 # $CONFIG['auth'] = 'ldap';
 $CONFIG['auth'] = 'default';
Â
+/************************************************************
+ * HTTP/LDAP detail configuration options                  *
+ ************************************************************/
+# $CONFIG['auth'] = 'httpldap';
+/* This is the field which contains user login */
+# $CONFIG['httpldap']['login'] = 'HTTP_AUTH_USER';
+/* This is the field which contains a URL redirect after logout */
+# $CONFIG['httpldap']['urlexit'] = 'http://';
Â
 /* TRANSLATION MODULE */
 #$CONFIG['translator']='none';
Â
httpldap module
This module is added to the directory /lib/modules/auth/. This module is a fake authenticator. Anyway, user is already authenticated.
show 2
Index: lib/modules/auth/httpldap.inc.php
===================================================================
@@ -0,0 +1,31 @@
+<?php
+
+require_once("ldap.inc.php");
+class httpldapAuth extends ldapAuth {
+
+Â function httpldapAuth() {
+Â }
+
+Â function init() {
+Â Â Â $this->config = app()->config['ldap'];
+Â Â Â $this->http = app()->config['httpldap'];
+Â Â Â $this->ufield = isset($this->config['uid'])?$this->config['uid']:'uid';
+Â Â Â $this->gfield = isset($this->config['gid'])?$this->config['gid']:'gid';
+
+Â Â Â /* Which field contains the user login ? */
+Â Â Â $this->http['login'] = isset($this->http['login'])?$this->http['login']:'HTTP_AUTH_USER';
+
+Â Â Â /* cannot add or edit users for now */
+Â Â Â $this->features = array('useradmin' => 'no', 'groupadmin' => 'no');
+Â }
+
+Â function authenticate($login,$password) {
+Â Â Â $result = false;
+Â Â Â if ($_SERVER{$this->http['login']} == $login)
+Â Â Â Â Â Â Â $result = true;
+Â Â Â return $result;
+Â }
+
+}
+?>
+
Authentication bypass
You need a bypass to avoid Open Upload's login form. In the following example, bypass is used if authentication type is httpldap. Authentication process will be called.
Loop problem
Details
The unauthenticated user has the default group unregister. The login action is available to user with default group (g and d actions are also available, but they aren't relevant for this problem). During authentication phase, if it's impossible to obtain the list of LDAP groups. User keeps the default group and an endless loop occurs.
Resolution
After authentication, if user keeps the default group, the program is stopped and an error message is displayed.
show 3
Index: lib/main.inc.php
===================================================================
@@ -485,9 +485,28 @@
          $this->db->free();
          exit(0);
        } else {
-Â Â Â Â Â Â Â Â Â /* save the requested url */
-Â Â Â Â Â Â Â Â Â redirect('?action=login');
-Â Â Â Â Â Â Â }
+Â Â Â Â Â Â Â Â /* Check if HTTP auth is used */
+Â Â Â Â Â Â Â Â Â if (($this->config['auth']=='httpldap') &&
+Â Â Â Â Â Â Â Â Â Â Â Â Â isset($_SERVER{$this->config['httpldap']['login']})) {
+
+Â Â Â Â Â Â Â Â Â Â Â Â Â $this->user->authenticate();
+
+Â Â Â Â Â Â Â Â Â Â Â Â Â if ($this->user->group() == $this->config['register']['nologingroup']) {
+Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â $this->log('error','login','','DENY',"this user isn't member any LDAP Openupload group or the software can't access informations about user");
+Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â $this->tpl->assign('user',$this->user->info());
+Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â $this->tpl->assign('langs',$this->langs);
+Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â unset($_SESSION['user']['messages']);
+Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â unset($_SESSION['user']['errors']);
+Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â $this->page['content']=tr('ACCESS DENIED TO THIS SOFTWARE!');
+Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â $this->tpl->assign('page',$this->page);
+Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â $this->display($this->mainPage);
+Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â $this->db->free();
+Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â Â exit(0);
+Â Â Â Â Â Â Â Â Â Â Â Â Â }
+Â Â Â Â Â Â Â Â Â } else {
+Â Â Â Â Â Â Â Â Â Â Â Â Â /* save the requested url */
+Â Â Â Â Â Â Â Â Â Â Â Â Â redirect('?action=login');
+Â Â Â Â Â Â Â Â Â }Â Â Â Â Â Â Â }
      }
      if ($_SERVER['QUERY_STRING']!='')
        $_SESSION['requested_url']='?'.$_SERVER['QUERY_STRING'];
Authentification and logout
logout function
This function is called when user logout. Instead of redirect user to Open Upload's login form, he is redirected to logout url.
authenticate function
This function is called during authentication phase. if authentication type is httpldap, user code is passed to the fake authenticator (httpldap). After the user information will be obtained from LDAP.
show 4
Index: lib/user.inc.php
===================================================================
@@ -19,7 +19,9 @@
    unset($_SESSION['user']);
    $_SESSION['user']['messages'] = $messages;
    $_SESSION['user']['errors'] = $errors;
-Â Â Â redirect('?action=login');
+
+Â Â Â $urlexit = isset(app()->config['httpldap']['urlexit'])?app()->config['httpldap']['urlexit']:'?action=login';
+Â Â Â redirect($urlexit);
  }
Â
  function loggedin() {
@@ -69,11 +71,17 @@
      return true;
Â
    // if it's logging in save user and pwd
-Â Â Â if (isset($_POST['username'])) {
+
+Â Â Â if ((app()->config['auth']=='httpldap') &&
+Â Â Â Â Â Â Â Â Â Â isset($_SERVER{app()->config['httpldap']['login']})) {
+Â Â Â Â Â $username = $_SERVER{app()->config['httpldap']['login']};
+Â Â Â Â Â $password = $_SERVER{app()->config['httpldap']['login']};
+Â Â Â }
+Â Â Â elseif (isset($_POST['username'])) {
      $username = $_POST['username'];
      $password = $_POST['pwd'];
    }
-
+
    if ($username != '') {
      // use the default authentication method
      $res = $this->auth->authenticate($username,$password);
Remove Open Upload's login form choice from menu
You must remove the choice login in menu.
show 5
Index: lib/modules/default/auth.inc.php
===================================================================
@@ -37,7 +37,10 @@
  function init() {
    if (!app()->user->loggedin()) {
-Â Â Â Â Â $this->menu['login']=tr('Login');
+Â Â Â Â Â Â Â // remove login choice in menu if HTTP auth is used
+Â Â Â Â Â Â Â if (app()->config['auth']!='httpldap') {
+Â Â Â Â Â Â Â Â Â Â $this->menu['login']=tr('Login');
+Â Â Â Â Â Â Â }
    } else {
      if (app()->auth->features['useradmin']=='yes')
        $this->menu['profile']=tr('Preferences');
Block access to the Open Upload's login form
Open Upload's login form is still available, you must block access. I use mod_rewrite to do this.
show 6
RewriteEngine On
RewriteCond %{QUERY_STRING} (a(.*)+=login)
RewriteRule ^(.*)$Â $1? [R=301,L]
Conclusion
Open Upload is an efficient application.  Among the free file download applications that I evaluated, it's more complete.